{json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET...
Transcript of {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET...
![Page 1: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/1.jpg)
{json:api}@speaktochris@NexmoDev
chris-guzman.com/jsonapi.pdf
![Page 2: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/2.jpg)
➡
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 3: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/3.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 4: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/4.jpg)
Ruby ! & Android "!
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 5: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/5.jpg)
{json:api}A specification for building APIs in
JSON
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 6: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/6.jpg)
{json:api}A specification for building APIs in
JSON(duh)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 7: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/7.jpg)
{json:api}Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 8: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/8.jpg)
{json:api}Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 9: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/9.jpg)
{"json":"api"}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 10: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/10.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 11: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/11.jpg)
Why?
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 12: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/12.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 13: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/13.jpg)
!
![Page 14: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/14.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 15: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/15.jpg)
- Minimize requests & data between clients & servers- Consistency, popular among consultancies
- Always backwards compatible- Stable 1.0, not dead
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 16: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/16.jpg)
No, really
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 17: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/17.jpg)
History
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 18: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/18.jpg)
!+"+#$+%=
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 19: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/19.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 20: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/20.jpg)
Spec
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 21: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/21.jpg)
- meta: a meta object that contains non-standard meta-information.
- errors: an array of error objects- OR -
- data: the document’s “primary data”
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 22: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/22.jpg)
Meta
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 23: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/23.jpg)
{ "meta": { "count": "42", "copyright": "Copyright 2015 Example Corp.", "authors": [ "Yehuda Katz", "Steve Klabnik", "Dan Gebhardt", "Tyler Kellen" ] }}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 24: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/24.jpg)
Errors
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 25: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/25.jpg)
{ "errors": [ "id": "UUID", "status": "418", "code": "42", "title": "You're a teapot", "detail": "The object is not short nor stout", "links": { "about": "https://httpstatuses.com/418" }, "meta": { "email": "[email protected]" } ]}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 26: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/26.jpg)
Data
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 27: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/27.jpg)
GET /articlesAccept: application/vnd.api+json
GET /articles/1Accept: application/vnd.api+json
GET /articles/1/authorAccept: application/vnd.api+json
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 28: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/28.jpg)
{ "data": { "type": "articles", "id": "1", "attributes": { "title": "Rails is Omakase" }, "relationships": {}, "links": { "self": "http://example.com/articles/1" }, }}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 29: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/29.jpg)
Links
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 30: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/30.jpg)
{"links": { "self": "/articles/1", "href": "http://example.com/articles/1" },}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 31: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/31.jpg)
Relationships
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 32: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/32.jpg)
{ "relationships": { "author": { "data": { "type": "people", "id": "9" }, "links": { "related": "/articles/1/author", "self": "/articles/1/relationships/author" } } }}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 33: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/33.jpg)
#Request comments with an articleGET /articles/1?include=comments
#Request authors & photos with an articleGET /articles/1?include=authors,photos
#Request comments as well as the author of each of those commentsGET /articles/1?include=comments.author
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 34: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/34.jpg)
{ "data":[], "included": [ { "type": "people", "id": "11", "attributes": { "name": "Oli Rumbelow", "email": "[email protected]" } }, { "type": "photos", "id": "45", "attributes": { "url": "http://www.example.com/foobar", "height": 1080, "width": 1920 }}]}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 35: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/35.jpg)
#Request authors with id of 1 or 2GET /authors/?filter[id]=1,2
#Request authors who are aliveGET /authors?filter[alive]=true
#Request comments published after a dateGET /comments?filter[published_after]=1990-01-01
Note: JSON:API is agnostic about how the filter query parameter can be used.Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 36: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/36.jpg)
#Request only the title, & status fieldsGET /articles?fields[articles]=title,status
#Request only the article's title & body fields#plus the name of the authorGET /articles/1?&fields[articles]=title,body\ include=author&fields[people]=name
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 37: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/37.jpg)
{"data": [ { "type": "articles", "id": "3", "attributes": { "title": "NodeJS Best Practices", "status": "published" } }]}Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 38: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/38.jpg)
#Sort articles alphabetically by titleGET /articles/?sort=title
#Sort authors by name, then lifeGET /authors?sort=name,alive
#Sort authors by reverse alphabetical order, then lifeGET /authors?sort=-name,alive
Note: JSON:API is agnostic about how the sort query parameter can be used.Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 39: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/39.jpg)
#Get the third of 13 pages, one article at a timeGET /articles?page[number]=3&page[size]=1
"links": { "self": "http://example.com/articles?page[number]=3&page[size]=1", "first": "http://example.com/articles?page[number]=1&page[size]=1", "prev": "http://example.com/articles?page[number]=2&page[size]=1", "next": "http://example.com/articles?page[number]=4&page[size]=1", "last": "http://example.com/articles?page[number]=13&page[size]=1"}
Note: JSON:API is agnostic about how the page query parameter can be used.Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 40: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/40.jpg)
GET /articles?include=comments,author &fields[people]=first_name,last_name &sort=-date
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 41: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/41.jpg)
GET /articles?include=comments,author &fields[people]=first_name,last_name &sort=-date
» fetch all articles with their associated comments and authors
» Only be return the first and last names
» Sorted by date, most recent first
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 42: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/42.jpg)
POST /photos{"data": { "type": "photos", "attributes": { "title": "Ember Hamster", "src": "http://example.com/images/productivity.png" }, "relationships": { "photographer": { "data": { "type": "people", "id": "9" } } } }}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 43: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/43.jpg)
PATCH /articles/1{"data": { "type": "articles", "id": "1", "attributes": { "title": "To TDD or Not", "text": "TLDR; It's complicated..." } }}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 44: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/44.jpg)
PATCH /articles/1/relationships/author
{ "data": { "type": "people", "id": "12" }}
PATCH /articles/1/relationships/tags
{ "data": [ { "type": "tags", "id": "2" }, { "type": "tags", "id": "3" } ]}
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 45: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/45.jpg)
PATCH /articles/1/relationships/author{"data": null}
PATCH /articles/1/relationships/tags{"data": []}
DELETE /photos/1#empty body
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 46: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/46.jpg)
JSON:API» Can take advantage of caching
» built on top of REST
vs GraphQL» Backed by heavier players
» GraphiQL UI
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 47: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/47.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 48: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/48.jpg)
Ok, maybe not the best analogy
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 49: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/49.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 50: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/50.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 51: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/51.jpg)
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf
![Page 52: {json:api} - Chris Gchris-guzman.com/talks/jsonapi.pdf · #Request authors with id of 1 or 2 GET /authors/?filter[id]=1,2 #Request authors who are alive GET /authors?filter[alive]=true](https://reader030.fdocuments.us/reader030/viewer/2022041017/5eca7b9903de2c4cd02dc333/html5/thumbnails/52.jpg)
{json:api}@speaktochris@NexmoDev
chris-guzman.com/jsonapi.pdf
Better APIs with JSON:API - @speaktochris - chris-guzman.com/jsonapi.pdf