0

Consider a web api exposing two kind of resources: Users and Teams with many-to-many relationship, typically a REST api will expose the following trivial endpoints to read data:

GET /users
GET /users/{id}
GET /users/{id}/teams
GET /teams
GET /teams/{id}
GET /teams/{id}/users

Now I am trying to design endpoints to manage relationships between the resources (endpoints to create/edit single resource through POST/PUT are trivial). For a simple situation, we want to attach/remove a team (already existing) to a user (already existing). Are the following endpoints REST-compliant?

1- POST /users/{id}/teams (content= team ID) : to link a team to user 
2- PUT /users/{id}/teams/{id-team} (no content) : to link a team to user 
3- DELETE /users/{id}/teams/{id-team} (no content) : to remove team link

Is there any other Idea of endpoints which can be more convenient to use? (without using a distinct endpoint for relation management, like /relations)

4
  • Can you state more specifically what you mean by "convenient?" Your second list of example URLs seems like they're as short as they can possibly be. Commented May 21, 2019 at 15:01
  • If you considered the link record as an entity in its own right, you could simply POST to /userteamrelations. Commented May 21, 2019 at 15:03
  • @RobertHarvey the second question is in the case for some reason one of my three proposals does not fit with REST conventions. And I cannot consider having a specific endpoint like your proposed /userteamrelations because I am not able to have a unique id for this kind of resource (because of legacy data structure), which means that I cannot have something like /userteamrelations/{id}
    – Oxald
    Commented May 22, 2019 at 6:13
  • So your main concern is conforming to "REST conventions?" I don't think you're going to get that anyway, since you don't have an ID available for these relations. Commented May 22, 2019 at 15:04

1 Answer 1

1

REST doesn't care what spelling you use for your URIs, beyond the basics that they conform with RFC 3986. The machines don't care after that, in much the same way that the compiler doesn't care what variable names you use. Follow any conventions you like.

If your URIs have a hierarchical structure, then you can take advantage of dot segments and relative resolution, which can be convenient.

However, you should be aware that the hierarchy implied by path segments in the URI does NOT actually imply a hierarchy of the resources. DELETE /A says absolutely nothing about /A/B or /A/B/C; a successful delete will instruct the client to invalidate /A from its local cache, but /A/B will be left untouched.

That it turn means that if you are trying to request a change to the relationship, the target URI for the request should match the uri of the relationship.

In your case, you want a URI design that allows you to encode within it two pieces of information for the server. Putting each of those pieces of information into a separate path segment is acceptable, and it may be easier to find routing implementations that support that schema, but you do have other choices available to you.

A common one would be to move the encoded information into the query part.

An uncommon one would both encoded values into the same path segment. Matrix parameters is a useful search term. RFC 3986 allows the use of : & , ; = in path segments, so that gives you options like

/c58ad7cc-18ab-48d4-ae7b-070d9461f69d/id=7;id-team=4
/c58ad7cc-18ab-48d4-ae7b-070d9461f69d/id:7,id-team:4

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.