Guidelines for returning a resource view, which is also a collection

Let's say I want to create a RESTful interface, and I want to work with foo based on their identifiers. Nothing new here:

  • GET /api/foo1 returns the view (e.g. using JSON) of foo1 .
  • DELETE /api/foo1 removes foo1 .

and etc.

Now let me tell you that "foo" is a collection type thing. So I want to add a “bar” to “foo”:

  • PUT /api/foo1/bar3 adds bar3 to foo1 .
  • GET /api/foo1/bar3 returns the view foo1 .
  • DELETE /api/foo1/bar3 removes bar3 from foo1 .
  • DELETE /api/foo1 completely removes foo1 .

Now the question remains: what does GET /api/foo1 do? It just returns a view of foo1 , as I originally assumed in this question? Or does it return a list of bars? Or does it return a representation of foo1 , which is both a description of foo1 and includes a list of all contained bars?

Or should GET /api/foo1 just return the view foo1 , as I assumed at the beginning, and request a PROPFIND request to display the columns inside foo1 (the approach adopted by WebDAV)? But in order to be consistent, do I need to change all my other list-type functions to PROPFIND , which directly contradicts all of these thousands of RESTful tutorials that say to use GET /api/foo1 to display content?

+7
rest get webdav
source share
3 answers

After some thought, I think the best conceptual explanation from a RESTful point of view is that usually a “thing” is not the same as its “collection”. Thus, although in the world of WebDAV a directory/ may be the same as its files, in the RESTful world I can have a separate subdirectory directory/files/ for the contained files. That way, I can manipulate directories separately from files that are stored.

Consider the RESTful API for a farm containing sheds. The endpoint farm/api/barns/ can return a list of barns, one of which will be farm/api/barns/bigredbarn . I farm/api/barns/bigredbarn/ think that extracting farm/api/barns/bigredbarn/ will provide me with a list of animals in the barn, which caused this question.

But actually the animals in the barn are just one aspect of the Big Red Barn. It may contain vehicles and hay:

  • farm/api/barns/bigredbarn/animals/
  • farm/api/barns/bigredbarn/vehicles/
  • farm/api/barns/bigredbarn/haybales/

With this approach, the dilemma I encountered does not arise.

+3
source share

The semantics of webdav have never been reconciled with RESTful idioms.

In theory, GET should get an idea of ​​the state of the resource, and PROPFIND should be used to retrieve the members of the collection.

So you have to do this:

  • GET / api / foo1 / - returns only the state foo1
  • PROPFIND / api / foo1 / - returns the members of foo1

Most interface developers will exit the game if you told them to use PROPFIND, although it is fully supported in js browser implementations.

Personally, I use the webdav / json gateway, where requests are executed using RESTful idioms, but redirected to my webdav implementation

For example, I would do the following:

 GET /api/foo1/_PROPFIND?fields=name,fooProp1,fooProp2 

And it will return

 [ { name : "bar1", fooProp1: "..", fooProp2 : ".."}, { name : "bar2", fooProp1: "..", fooProp2 : ".."} ] 

One of the advantages of this approach is that the client gets the ability to control the return properties of json. This is good because a rich API will have many properties, but in most cases, clients do not need all of them.

+2
source share

Routes and their actions in the RESTfull API are fully developed by developers. This is a developer who decides what to return when requesting a specific route, say GET /api/foo1 .

And the developer must design each route, including /api/foo1/bar . There is no specific rule as to what a particular route should do. If your API is an open source project, you’ll get crisp and clear documentation for each route.

Do not waste time thinking about old school strategies.

+1
source share

All Articles