I have RESTful API within a web-service with some kind of resources like users, posts and so on. When I make request for list of posts (GET /posts), I want to retrieve array of posts only with reduced part of data for each post (i.e. subject, author name). When I make request for concrete post (GET /posts/42) I want to retrieve full list of post object fields, including big post body, additional info about likes count, comments count.
I suppose it is exists many ways to solve this problem. In my mind, 3 most obvious are:
- Explicitly specify fields lits on every request
(/posts?fileds=subject,author_name and for
/posts/42?fields=subject,body,createaAt,author_name,comments_count,likes_count,etc...).
- Explicitly specify fields list only if it differs from default
fields list.
- Specify fields list that should be excluded
(or inlcuded) from (to) default fields set if desired fields set differs from default.
I what to build clear and useful API for my customers. Which way should I choose?
I'd go for option 2 IMHO.
So if the consumer just requests the resource url (/posts/42
) they receive the default fields.
Then consumers can alter the default response by defining values in the query string like:
/posts/42/fields?subject,author_name
This has worked well for me in the past and is how some other well know APIs work, e.g. Facebook
Edit: Looking back at this I’d change the request to be:
/posts/42?fields=subject,author_name
/post/42
is the resource, not fields.
Have been doing research into this as well and was pointed towards Facebook's GraphQL as an alternative to requesting a restful api with the fields wanted. It is still in the very early stages but seems very promising.
https://facebook.github.io/react/blog/2015/05/01/graphql-introduction.html
EDIT:
Reproduced from the URL:
A GraphQL query is a string interpreted by a server that returns data in a specified format. Here is an example query:
{
user(id: 3500401) {
id,
name,
isViewerFriend,
profilePicture(size: 50) {
uri,
width,
height
}
}
}
(Note: this syntax is slightly different from previous GraphQL examples. We've recently been making improvements to the language.)
And here is the response to that query.
{
"user" : {
"id": 3500401,
"name": "Jing Chen",
"isViewerFriend": true,
"profilePicture": {
"uri": "http://someurl.cdn/pic.jpg",
"width": 50,
"height": 50
}
}
}