issue_comments

24 rows where issue = 502993509 sorted by updated_at descending

View and edit SQL

Suggested facets: created_at (date), updated_at (date)

user

issue

  • Redesign register_output_renderer callback · 24

author_association

id html_url issue_url node_id user created_at updated_at ▲ author_association body reactions issue
635055346 https://github.com/simonw/datasette/issues/581#issuecomment-635055346 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNTA1NTM0Ng== simonw 9599 2020-05-28T02:24:14Z 2020-05-28T02:24:14Z OWNER

Updated documentation is here: https://datasette.readthedocs.io/en/latest/plugins.html#register-output-renderer-datasette

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634879258 https://github.com/simonw/datasette/issues/581#issuecomment-634879258 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg3OTI1OA== simonw 9599 2020-05-27T19:09:22Z 2020-05-28T01:33:45Z OWNER

OK, the new design: your callback function can take any of the following arguments:

  • datasette - a Datasette instance
  • columns - the list of columns
  • rows - the list of rows (each one a SQLite Row object)
  • sql - the SQL query being executed
  • query_name - the name of the canned query, if this is one
  • database - the database name
  • table - the table or view name
  • request - the request object (to be documented in #706)
  • view_name - the name of the view

We will also continue to support the existing args and data arguments, but these will be undocumented and will be deprecated in Datasette 1.0. UPDATE: Decided against this, see https://github.com/simonw/datasette/issues/581#issuecomment-634946197

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634978388 https://github.com/simonw/datasette/issues/581#issuecomment-634978388 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk3ODM4OA== simonw 9599 2020-05-27T22:32:03Z 2020-05-27T22:32:03Z OWNER

Request object is now documented: https://datasette.readthedocs.io/en/latest/internals.html#request-object

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634964457 https://github.com/simonw/datasette/issues/581#issuecomment-634964457 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk2NDQ1Nw== simonw 9599 2020-05-27T21:57:35Z 2020-05-27T21:57:35Z OWNER

(I wonder if this would be enough to allow really smart plugins to implement ETag/conditional get)

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634964294 https://github.com/simonw/datasette/issues/581#issuecomment-634964294 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk2NDI5NA== simonw 9599 2020-05-27T21:57:10Z 2020-05-27T21:57:10Z OWNER

Right now a rendering callback returns the following:

body - string or bytes, optional
    The response body, default empty
content_type - string, optional
    The Content-Type header, default text/plain
status_code - integer, optional
    The HTTP status code, default 200 

I'm going to add an optional headers dictionary key, too.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634946319 https://github.com/simonw/datasette/issues/581#issuecomment-634946319 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk0NjMxOQ== simonw 9599 2020-05-27T21:18:50Z 2020-05-27T21:18:50Z OWNER

(I used GitHub code search to find code using this plugin hook: https://github.com/search?q=register_output_renderer&type=Code )

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634946197 https://github.com/simonw/datasette/issues/581#issuecomment-634946197 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk0NjE5Nw== simonw 9599 2020-05-27T21:18:30Z 2020-05-27T21:18:30Z OWNER

I'm going to break backwards compatibility directly here, without waiting for Datasette 1.0.

The reason is that https://github.com/russss/datasette-geo hasn't been updated in 13 months so is already broken against current Datasette, and the other two plugins using this hook are owned by me so I can upgrade them myself.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634944832 https://github.com/simonw/datasette/issues/581#issuecomment-634944832 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk0NDgzMg== simonw 9599 2020-05-27T21:15:50Z 2020-05-27T21:16:28Z OWNER

It bothers me that query_name here means the configured name of the canned query, but view_name means the name of the Datasette view class, NOT the name of an associated SQL view. That's in table.

Can I come up with clearer names for these?

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634943336 https://github.com/simonw/datasette/issues/581#issuecomment-634943336 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDk0MzMzNg== simonw 9599 2020-05-27T21:13:04Z 2020-05-27T21:13:04Z OWNER

Since I'm passing request I won't pass scope - if people want that they can access request.scope.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
592621235 https://github.com/simonw/datasette/issues/581#issuecomment-592621235 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDU5MjYyMTIzNQ== simonw 9599 2020-02-28T17:24:06Z 2020-05-27T21:12:21Z OWNER

Rather than pass a request object (hence promoting that object into part of the documented, stable API) I think I'll pass the ASGI scope - that's already a stable, documented standard.

UPDATE: changed my mind since request is used by other plugins too, see #706.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634921101 https://github.com/simonw/datasette/issues/581#issuecomment-634921101 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDkyMTEwMQ== simonw 9599 2020-05-27T20:27:36Z 2020-05-27T20:27:36Z OWNER

Actually passing the request object would be OK if I document it see https://github.com/simonw/datasette/issues/706

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634893744 https://github.com/simonw/datasette/issues/581#issuecomment-634893744 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg5Mzc0NA== simonw 9599 2020-05-27T19:32:08Z 2020-05-27T19:32:08Z OWNER

Need to figure out how best to unit test this plugin hook.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634888582 https://github.com/simonw/datasette/issues/581#issuecomment-634888582 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg4ODU4Mg== simonw 9599 2020-05-27T19:23:23Z 2020-05-27T19:23:23Z OWNER

Here's the function I just wrote for this:

def call_with_supported_arguments(fn, **kwargs):
    parameters = inspect.signature(fn).parameters.keys()
    call_with = []
    for parameter in parameters:
        if parameter not in kwargs:
            raise TypeError("{} requires parameters {}".format(fn, tuple(parameters)))
        call_with.append(kwargs[parameter])
    return fn(*call_with)
{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634882770 https://github.com/simonw/datasette/issues/581#issuecomment-634882770 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg4Mjc3MA== simonw 9599 2020-05-27T19:16:19Z 2020-05-27T19:16:19Z OWNER
In [1]: import inspect                                                                                                                                                             

In [2]: def foo(view, sql, inspect): 
   ...:     pass 
   ...:                                                                                                                                                                            

In [3]: inspect.signature(foo)                                                                                                                                                     
Out[3]: <Signature (view, sql, inspect)>

In [4]: inspect.signature(foo).parameters                                                                                                                                          
Out[4]: 
mappingproxy({'view': <Parameter "view">,
              'sql': <Parameter "sql">,
              'inspect': <Parameter "inspect">})

In [5]: inspect.signature(foo).parameters.keys()                                                                                                                                   
Out[5]: odict_keys(['view', 'sql', 'inspect'])

In [6]: set(inspect.signature(foo).parameters.keys())                                                                                                                              
Out[6]: {'inspect', 'sql', 'view'}
{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634882112 https://github.com/simonw/datasette/issues/581#issuecomment-634882112 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg4MjExMg== simonw 9599 2020-05-27T19:14:55Z 2020-05-27T19:14:55Z OWNER

https://docs.python.org/3/library/inspect.html#introspecting-callables-with-the-signature-object

New in version 3.3.

The Signature object represents the call signature of a callable object and its return annotation. To retrieve a Signature object, use the signature() function.

inspect.``signature(callable, *, follow_wrapped=True)

Return a Signature object for the given callable:

```

from inspect import signature
def foo(a, , b:int, *kwargs):
... pass

sig = signature(foo)

str(sig)
'(a, , b:int, *kwargs)'

str(sig.parameters['b'])
'b:int'

sig.parameters['b'].annotation
<class 'int'>
```

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634881287 https://github.com/simonw/datasette/issues/581#issuecomment-634881287 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg4MTI4Nw== simonw 9599 2020-05-27T19:13:09Z 2020-05-27T19:13:09Z OWNER

I think I need a utility function for "call this function with this dictionary of arguments, but only pass the arguments which are inspected by the function".

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634879734 https://github.com/simonw/datasette/issues/581#issuecomment-634879734 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg3OTczNA== simonw 9599 2020-05-27T19:10:17Z 2020-05-27T19:12:36Z OWNER

The should_suggest callback will take the same arguments: https://github.com/simonw/datasette/issues/770#issuecomment-634880090

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634865620 https://github.com/simonw/datasette/issues/581#issuecomment-634865620 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg2NTYyMA== simonw 9599 2020-05-27T18:44:06Z 2020-05-27T18:44:06Z OWNER

The existing render callback takes the following arguments:

args - dictionary
The GET parameters of the request

data - dictionary
The data to be rendered

view_name - string
The name of the view where the renderer is being called. (index, database, table, and row are the most important ones.)

The data argument is a bit of a problem, because it tightly couples plugins to a currently undocumented datastructure within Datasette. Here's how datasette-atom picks that apart for example: https://github.com/simonw/datasette-atom/blob/095941c23c81b70c4787cdeef873c556b573b5fa/datasette_atom/init.py#L15-L66 - it does things like access data["query"]["sql"] to figure out the SQL query that was used.

I'm going to change the design of part of this ticket. I won't break the old data value just yet, but I'll mark it to be deprecated by Datasette 1.0.

I think the only plugins using it right now are my datasette-atom and datasette-ics and @russss's datasette-geo so hopefully changing this won't cause any wider damage.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634857975 https://github.com/simonw/datasette/issues/581#issuecomment-634857975 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg1Nzk3NQ== simonw 9599 2020-05-27T18:30:29Z 2020-05-27T18:30:29Z OWNER

I'll use #770 for the should_suggest mechanism - this issue is for the extra arguments passed to the rendering callback.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634856748 https://github.com/simonw/datasette/issues/581#issuecomment-634856748 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg1Njc0OA== simonw 9599 2020-05-27T18:28:32Z 2020-05-27T18:28:32Z OWNER

Here's the code that passes a list of renderers to the template:

https://github.com/simonw/datasette/blob/2d099ad9c657d2cab59de91cdb8bfed2da236ef6/datasette/views/base.py#L411-L423

A renderer is currently defined as a two-key dictionary:

@hookimpl
def register_output_renderer(datasette):
    return {
        'extension': 'test',
        'callback': render_test
    }

I can add a third key, "should_suggest" which is a function that returns True or False for a given query. If that key is missing it is assumed to return True.

One catch: what arguments should be passed to the should_suggest(...) function?

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634853296 https://github.com/simonw/datasette/issues/581#issuecomment-634853296 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg1MzI5Ng== simonw 9599 2020-05-27T18:22:46Z 2020-05-27T18:22:46Z OWNER

While I'm doing this, another feature I would like is the ability for renderers to opt-in / opt-out of being displayed as options on the page.

https://www.niche-museums.com/browse/museums for example shows a atom link because the datasette-atom plugin is installed... but clicking it will give you a 400 error because the correct columns are not present:

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
634852196 https://github.com/simonw/datasette/issues/581#issuecomment-634852196 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDYzNDg1MjE5Ng== simonw 9599 2020-05-27T18:20:46Z 2020-05-27T18:20:46Z OWNER

Here's the code that calls the renderers - this needs to be expanded to check for those extra optional arguments:

https://github.com/simonw/datasette/blob/2d099ad9c657d2cab59de91cdb8bfed2da236ef6/datasette/views/base.py#L387-L398

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
569005894 https://github.com/simonw/datasette/issues/581#issuecomment-569005894 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDU2OTAwNTg5NA== simonw 9599 2019-12-26T08:03:59Z 2019-12-26T08:03:59Z OWNER

To solve https://github.com/simonw/datasette-atom/issues/6 the name of the current canned query should be made available somehow.

That way the plugin configuration could specify that the title for browse/feed should be X.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509
538672413 https://github.com/simonw/datasette/issues/581#issuecomment-538672413 https://api.github.com/repos/simonw/datasette/issues/581 MDEyOklzc3VlQ29tbWVudDUzODY3MjQxMw== simonw 9599 2019-10-05T17:45:04Z 2019-10-05T17:45:04Z OWNER

The request object should be made available too.

{
    "total_count": 0,
    "+1": 0,
    "-1": 0,
    "laugh": 0,
    "hooray": 0,
    "confused": 0,
    "heart": 0,
    "rocket": 0,
    "eyes": 0
}
Redesign register_output_renderer callback 502993509

Advanced export

JSON shape: default, array, newline-delimited, object

CSV options:

CREATE TABLE [issue_comments] (
   [html_url] TEXT,
   [issue_url] TEXT,
   [id] INTEGER PRIMARY KEY,
   [node_id] TEXT,
   [user] INTEGER REFERENCES [users]([id]),
   [created_at] TEXT,
   [updated_at] TEXT,
   [author_association] TEXT,
   [body] TEXT,
   [reactions] TEXT,
   [issue] INTEGER REFERENCES [issues]([id])
);
CREATE INDEX [idx_issue_comments_issue]
                ON [issue_comments] ([issue]);
CREATE INDEX [idx_issue_comments_user]
                ON [issue_comments] ([user]);
Powered by Datasette · Query took 28.698ms · About: github-to-sqlite