RESTful API - URI

I have a REST API URL structure similar to:

/api/contacts GET Returns an array of contacts /api/contacts/:id GET Returns the contact with id of :id /api/contacts POST Adds a new contact and return it with an id added /api/contacts/:id PUT Updates the contact with id of :id /api/contacts/:id PATCH Partially updates the contact with id of :id /api/contacts/:id DELETE Deletes the contact with id of :id 

My question is:

 /api/contacts/:id GET 

Suppose that in addition to retrieving a contact by identifier, I also want to get it using a unique alias.

What should be the structure of a URI if I want to get a contact using ID or Alias?

+6
source share
4 answers

Part of the IRI requests and requests is up to you. The path is for hierarchical data, such as api/version/module/collection/item/property , the query is for non-hierarchical data, such as ?display-fields="id,name,etc..." or ?search="brown teddy bear"&offset=125&count=25 etc.

What you should keep in mind is that you work with resources, not operations. Thus, IRIs are resource identifiers, such as DELETE /something , and not operation identifiers, such as POST /something/delete . You do not have to follow any IRI structure, so for example, you can just use POST /dashuif328rgfiwa . The server would understand, but it would be more difficult to write a router for such an IRI, so we use good IRI.

It is important that one IRI always belongs to only one resource. Thus, you cannot read cat properties using GET /cats/123 and write dog properties using PUT /cats/123 . As a rule, ppl does not understand that one resource can have several IRIs, therefore, for example, /cats/123 , /cats/name:kitty , /users/123/cats/kitty , cats/123?fields="id,name" etc ... may belong to the same resource. Or, if you want to give IRI something (a live cat, not a document that describes it), you can use /cats/123#thing or /users/123#kitty , etc ... Usually you do this is in RDF docs.

What should be the structure of a URI if I want to get a contact using an identifier or alias?

It can be /api/contacts/name:{name} for example /api/contacts/name:John , since it is clearly hierarchical. Or you can check if the parameter contains numeric or string in /api/contacts/{param} .

You can also use the query, but I do not recommend doing this. For example, the following IRI can have two separate values: /api/contacts?name="John" . Do you want to list each contact with the name John or want to get an exact contact. Therefore, you need to make some conventions about these types of requests in the router of your server-side application.

+2
source

If you are an alias, not a numeric, I would suggest using the same URI structure and find out if it is an identifier or an alias at your end. Just like Facebook does with username and user_id. facebook.com/user_id or facebook.com/username.

Another approach would be for the client to use GET / contacts with some additional GET parameters as filters for the first search for the contact, and then to search for the identifier from this answer.

The last option, I think, will use a structure like GET / contacts / alias /: alias. But this will mean that the alias is an auxiliary source of contacts.

+4
source

I would think of adding a “search” resource when you are trying to resolve a resource with an alias:

 GET /api/contacts/:id 

and

 GET /api/contacts?alias=:alias 

or

 GET /api/contacts/search?q=:alias 
+1
source

First of all, the identifier in the URL does not have to be the numeric identifier generated by your database. You can use any piece of data (including an alias) in the URL as long as it is unique. Of course, if you use a numerical identifier everywhere, then in your API it is more consistent to do the same. But you can use aliases instead of numeric identifiers (if they are always unique).

Another approach would be, as suggested by Stromgren , to allow both numeric identifiers and aliases in the URL:

 /api/contacts/123 /api/contacts/foobar 

But this can obviously cause problems if the aliases can be numeric, because then you would have no way to differentiate the identifier and the (numeric) alias.

Last but not least, you can implement a way to filter the entire collection, since shlomi33 has already been proposed. I would not have presented a search resource, since this is actually not RESTful, so I would have chosen a different solution:

 /api/contacts?alias=foobar 

Which should return all contacts with foobar as an alias. Since the alias must be unique, this returns 1 or 0 results.

+1
source

Source: https://habr.com/ru/post/974731/


All Articles