{"html_url": "https://github.com/simonw/datasette/issues/828#issuecomment-641710670", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/828", "id": 641710670, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MTcxMDY3MA==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T04:19:17Z", "updated_at": "2020-06-10T04:19:17Z", "author_association": "OWNER", "body": "This CSS seems to fix it:\r\n```css\r\na.external {overflow-wrap: anywhere;}\r\n```", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 635914822, "label": "Horizontal scrollbar on changelog page on mobile"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/828#issuecomment-641710745", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/828", "id": 641710745, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MTcxMDc0NQ==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T04:19:31Z", "updated_at": "2020-06-10T04:19:31Z", "author_association": "OWNER", "body": "https://docs.readthedocs.io/en/stable/guides/adding-custom-css.html", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 635914822, "label": "Horizontal scrollbar on changelog page on mobile"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/828#issuecomment-641713087", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/828", "id": 641713087, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MTcxMzA4Nw==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T04:28:17Z", "updated_at": "2020-06-10T04:28:17Z", "author_association": "OWNER", "body": "Fixed. https://datasette.readthedocs.io/en/latest/changelog.html\r\n\r\n\"Changelog_\u2014_Datasette_documentation\"\r\n", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 635914822, "label": "Horizontal scrollbar on changelog page on mobile"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/394#issuecomment-641889565", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/394", "id": 641889565, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MTg4OTU2NQ==", "user": {"value": 58298410, "label": "LVerneyPEReN"}, "created_at": "2020-06-10T09:49:34Z", "updated_at": "2020-06-10T09:49:34Z", "author_association": "NONE", "body": "Hi,\r\n\r\nI came across this issue while looking for a way to spawn Datasette as a SQLite files viewer in JupyterLab. I found https://github.com/simonw/jupyterserverproxy-datasette-demo which seems to be the most up to date proof of concept, but it seems to be failing to list the available db (at least in the Binder demo, https://hub.gke.mybinder.org/user/simonw-jupyters--datasette-demo-uw4dmlnn/datasette/, I only have `:memory`).\r\n\r\nDoes anyone tried to improve on this proof of concept to have a Datasette visualization for SQLite files?\r\n\r\nThanks!", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 396212021, "label": "base_url configuration setting"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/394#issuecomment-641908346", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/394", "id": 641908346, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MTkwODM0Ng==", "user": {"value": 127565, "label": "wragge"}, "created_at": "2020-06-10T10:22:54Z", "updated_at": "2020-06-10T10:22:54Z", "author_association": "CONTRIBUTOR", "body": "There's a working demo here: https://github.com/wragge/datasette-test\r\n\r\nAnd if you want something that's more than just proof-of-concept, here's a notebook which does some harvesting from web archives and then displays the results using Datasette: https://nbviewer.jupyter.org/github/GLAM-Workbench/web-archives/blob/master/explore_presentations.ipynb", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 396212021, "label": "base_url configuration setting"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/829#issuecomment-642161210", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/829", "id": 642161210, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjE2MTIxMA==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T17:45:58Z", "updated_at": "2020-06-10T17:45:58Z", "author_association": "OWNER", "body": "`itsdangerous` has this ability but you specify the max-age when you call unsign: https://itsdangerous.palletsprojects.com/en/1.1.x/timed/\r\n\r\n> s.unsign(string, max_age=5)\r\n> Traceback (most recent call last):\r\n> ...\r\n> itsdangerous.exc.SignatureExpired: Signature age 15 > 5 seconds\r\n\r\nI currently only decode the `ds_actor` cookie in one place: https://github.com/simonw/datasette/blob/d828abaddec0dce3ec4b4eeddc3a74384e52cf34/datasette/actor_auth_cookie.py#L5-L12\r\n\r\nIf plugins want to be able to set their own policies on how long the `ds_actor` cookie should remain valid, how do I know to listen to them when decoding the cookie here?", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636426530, "label": "Ability to set ds_actor cookie such that it expires"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/829#issuecomment-642174272", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/829", "id": 642174272, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjE3NDI3Mg==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T18:10:13Z", "updated_at": "2020-06-10T18:10:13Z", "author_association": "OWNER", "body": "Some options:\r\n\r\n- Redesign the `ds_actor` cookie to be `{\"expires_at\": 1591811250, \"actor\": ...}` - check if it has expired in that default `actor_from_request` hook\r\n- Let plugins set an additional cookie of some sort\r\n- Expect plugins that care about this to set a cookie with a different name and implement their own `actor_from_request` against that", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636426530, "label": "Ability to set ds_actor cookie such that it expires"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/829#issuecomment-642175892", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/829", "id": 642175892, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjE3NTg5Mg==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T18:13:26Z", "updated_at": "2020-06-10T18:13:26Z", "author_association": "OWNER", "body": "I'm going with `expires_at` - except to keep the cookies shorter the key will be called `e` and the actor will go in `a`, like this:\r\n\r\n```json\r\n{\r\n \"e\": \"1UuHoo\",\r\n \"a\": {\"id\": \"root\"}\r\n}\r\n```\r\nThat `e` value is a base64 encoded expiry integer timestamp (again for a shorter cookie) - using https://pypi.org/project/python-baseconv/", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636426530, "label": "Ability to set ds_actor cookie such that it expires"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/829#issuecomment-642176180", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/829", "id": 642176180, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjE3NjE4MA==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T18:14:02Z", "updated_at": "2020-06-10T18:14:15Z", "author_association": "OWNER", "body": "And the `e` key can be `null`or missing for \"never expires\".", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636426530, "label": "Ability to set ds_actor cookie such that it expires"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/829#issuecomment-642178604", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/829", "id": 642178604, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjE3ODYwNA==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T18:18:36Z", "updated_at": "2020-06-10T18:20:19Z", "author_association": "OWNER", "body": "Even shorter: encode an integer that is the difference between that expiry timestamp and a more recent epoch - June 1st 2020 will do.\r\n\r\n```\r\n>>> import datetime, calendar\r\n>>> calendar.timegm(datetime.date(2020, 6, 1).timetuple())\r\n1590969600\r\n>>> import baseconv\r\n>>> baseconv.base62.encode(int(time.time() - 1590969600))\r\n'3XST'\r\n```", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636426530, "label": "Ability to set ds_actor cookie such that it expires"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/829#issuecomment-642217520", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/829", "id": 642217520, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjIxNzUyMA==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T19:41:35Z", "updated_at": "2020-06-10T19:41:35Z", "author_association": "OWNER", "body": "I didn't bother with the alternative epoch - it only shaves off two or three bytes from the cookie.\r\n\r\nDocumentation for the new `ds_actor` cookie shape is here: https://datasette.readthedocs.io/en/latest/authentication.html#the-ds-actor-cookie", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636426530, "label": "Ability to set ds_actor cookie such that it expires"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/818#issuecomment-642229899", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/818", "id": 642229899, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjIyOTg5OQ==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T20:07:36Z", "updated_at": "2020-06-10T20:07:36Z", "author_association": "OWNER", "body": "New policy in 9f236c4 dictates that this should be in Milestone 0.44 after all:\r\n\r\n> * **New plugin hooks** should only be shipped if accompanied by a separate release of a non-demo plugin that uses them.", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 634917088, "label": "Example permissions plugin"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/818#issuecomment-642230499", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/818", "id": 642230499, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjIzMDQ5OQ==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T20:08:46Z", "updated_at": "2020-06-10T20:09:26Z", "author_association": "OWNER", "body": "What's a simple but useful plugin I could release that exercises this hook?\r\n\r\nIdeally one which executes permission checks against the database somehow.\r\n\r\nI could do a simplest-possible implementation of the idea in #801 (allow-by-query).", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 634917088, "label": "Example permissions plugin"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/818#issuecomment-642231871", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/818", "id": 642231871, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjIzMTg3MQ==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T20:11:50Z", "updated_at": "2020-06-10T20:11:50Z", "author_association": "OWNER", "body": "`datasette-permissions-sql`\r\n```yaml\r\nplugins:\r\n datasette-permissions-sql:\r\n view-instance: |-\r\n select count(*) from users where admin = 1 and id = :id\r\n```", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 634917088, "label": "Example permissions plugin"}, "performed_via_github_app": null} {"html_url": "https://github.com/simonw/datasette/issues/831#issuecomment-642324847", "issue_url": "https://api.github.com/repos/simonw/datasette/issues/831", "id": 642324847, "node_id": "MDEyOklzc3VlQ29tbWVudDY0MjMyNDg0Nw==", "user": {"value": 9599, "label": "simonw"}, "created_at": "2020-06-10T23:50:55Z", "updated_at": "2020-06-10T23:50:55Z", "author_association": "OWNER", "body": "Actually I'm not sure about this. If `\"allow\": null` means \"no-one can do this\", what's the allow block syntax for \"everyone can do this\"?\r\n\r\nIt could be `\"allow\": {}` - but that's not intuitive because normally the allow block shows keys that need to match. `{}` suggests to me that no matches are possible.\r\n\r\nSo I think I'm going to stick with the current mechanism, which is that `\"allow\": null` means \"anyone can do this\" and `\"allow\": {}` means \"no-one can do this\".", "reactions": "{\"total_count\": 0, \"+1\": 0, \"-1\": 0, \"laugh\": 0, \"hooray\": 0, \"confused\": 0, \"heart\": 0, \"rocket\": 0, \"eyes\": 0}", "issue": {"value": 636614868, "label": "It would be more intuitive if \"allow\": none meant \"no-one can do this\""}, "performed_via_github_app": null}