3 ms·
> GitHub’s REST api is pretty self discoverable fwiw. I had a look at the example response to see whether that is true. I give you that there are hyperlinks ex
by bmn__ 4y ago
> GitHub’s REST api is pretty self discoverable fwiw.
I had a look at the example response to see whether that is true. I give you that there are hyperlinks existing in resources of media type `application/vnd.github+json`, but there is no uniform interface to discover a link. Fielding would disapprove. It's an indication of bad design that a client must hardcode e.g. `labels_url` instead of having a generic reusable way to access a link that works across a multitude of JSON derived media types.
- munk-a 4y agoWouldn't any interface to discover links need to be hardcoded? IIRC, REST didn't actually define a unified way to describe where the links existed in the returned document.
- bmn__ 4y agoThat's because you're looking at the wrong place, that's not the responsibility of REST: it can't because it's not a specification, but a description of an architectural style. Instead, it's the responsibility of the media type. HTML offers hypermedia controls: hyperlinks are denoted with <a>, <area>, <base>, <link> elements and the "href" attribute; forms are denoted with the <form> element as its "action" attribute. I assume you are familiar with HTML, you can see that this is a very generalised way to find links (or controls in general), it is applicable to all HTML documents. XML has close analogues: XLink and XForms. JSON-done-right offers hypermedia controls: moral equivalent of links <https://datatracker.ietf.org/doc/html/draft-kelly-json-hal#section-5.1 https://datatracker.ietf.org/doc/html/draft-kelly-json-hal#s...>, moral equivalent of forms <https://rwcbook.github.io/hal-forms/ https://rwcbook.github.io/hal-forms/>. It is easy to reimagine `application/vnd.github+json` in the guise of this media type so that the problem I was describing earlier disappears. If a media type cannot express hypermedia controls or link relations inline (e.g. WebP images), then the HTTP header can be used instead, see RFCs 8288 and 6570.
- munk-a 4y agoI can run a regex to find <a> tags as well as the next guy[1] but what do those links mean? Is one of those links a link to delete the object I am viewing and one of them a link to update it? What about the link to get a list of all the foos associated with this particular bar? How am I supposed to parse this blob of HTML programmatically to figure out which link is mapped to which action? I think this is where I think the big failing of original REST comes into play - these self-discoverable actions are sort of impossible to actually leverage... either you're hardcoding some information about the format (i.e. look for the <a class='delete'>) or you're automatically deriving the link anyways... there isn't really a reasonable way for REST to work where these links are self-descriptive enough for a machine to figure out on their own so... in the end... why not just separate that information out into a nicely formatted API document that the devs can have on hand while building their interoperable tool? 1. And personally prefer to always parse my HTML with regexes of course...
- bmn__ 4y ago> what do those links mean? […] figure out which link is mapped to which action The meaning is expressed by the link relation, see <https://news.ycombinator.com/item?id=32155744 https://news.ycombinator.com/item?id=32155744>. > Is one of those links a link to delete the object I am viewing and one of them a link to update it? Sure, see RFC 5023 § 11.1. > What about the link to get a list of all the foos associated with this particular bar? Okay, custom link relations since the existing predefined ones are insufficient. Because `foo` and `bar` are vague, I have to make up some details and can show one way to do it: GET /bar/this-particular HTTP/1.1 Host: munk-a.example HTTP/1.1 200 OK Link: </ns-rel/bar>; rel="type" Link: </collection/foo?filter=/bar/this-particular>; rel="/ns-rel/foo"; title="list of all the foos associated with this particular bar" Link: </bar/this-particular>; rel="self" Link: </collection/bar>; rel="collection /ns-rel/bar"; title="list of all bars" Content-Type: application/octet-stream … GET /collection/foo?filter=/bar/this-particular HTTP/1.1 Host: munk-a.example HTTP/1.1 200 OK Link: </ns-rel/foo>; rel="type" Link: </foo/some>; rel="item /ns-rel/foo"; title="some foo" Link: </foo/another>; rel="item /ns-rel/foo"; title="another foo" Link: </collection/foo?filter=/bar/this-particular>; rel="self start" Link: </collection/foo?filter=/bar/this-particular;page=2>; rel="next" Link: </collection/foo?filter=/bar/this-particular;page=11>; rel="last" Content-Type: multipart/mixed … > impossible […] there isn't really a reasonable way I'm skipping over the rant in the second paragraph which is clearly based on misunderstanding of the subject matter. Instead of baseless assertions, stick to asking questions if you don't want to make HN readers think you're an ignorant fool.