Standard REST API Design Convention - rest

Speaking of strict REST API design conventions, can a single resource correspond to multiple routes.
For example, I have the routes:
http://www.example.com/registrations
http://www.example.com/confirmations
http://www.example.com/unlocks
All these endpoints make use of the user resource to register a new user, confirm a user using confirmation token, and unlock a user using unlock token.
Is this correct REST design?

Well it's not wrong, but on top of that you're also probably going to have a /user endpoint, so there might be better ways of scaling this.
For example, the unlock might simply be a PUT on said /user, with a
{
"state": "unlocked" //active, whatever
}
I don't know the full extent of your API, but you can play with either http verbs like I did above, or POSTing different payloads to the same endpoint (for example having a confirmationToken as a property in the body for Registration, and reusing that endpoint, too).

Related

RESTful way to specify commands on a resource

I could not find a universally agreeable way to specify commands in RESTful manner. Consider that I have a resource on which I want to provide 3 commands:
enable
disable
re-trigger
Which is the most RESTful way?
POST /resource/disable
POST /resource?command=disable
Any other way ?
Which is the most RESTful way?
How would you do it with a web site? REST is the architectural style of the world wide web; if you can figure out how you would do it with a web site, that will give you the right idea for how to provide a RESTful API.
On the web, the usual answer would be that we would have forms to collect information from the client, who would then submit a POST request (because we are intending to change the resource) to some endpoint.
Because the form.action property tells the client what URI to use, the server has control over what the URI is -- we can change it later if we want to.
We could, as you suggest, have a different URI for each command. There's nothing wrong with that, but it does miss an opportunity. You see, one of the important ideas in REST is caching; and HTTP defines cache invalidation semantics; the practical aspect of which is that if you use the /resource identifier as the form action, then successful POST requests will automatically invalidate the client's local copies of the resource.
This does imply, of course, that the POST handler in your implementation will have to determine which command was intended -- probably by looking at information included in the body of the post request; a "commandName" parameter or something similar.

REST API design for resource modification: catch all POST vs multiple endpoints

I'm trying to figure out best or common practices for API design.
My concern is basically this:
PUT /users/:id
In my view this endpoint could by used for a wide array of functions.
I would use it to change the user name or profile, but what about ex, resetting a password?
From a "model" point of view, that could be flag, a property of the user, so it would "work" to send a modification.
But I would expect more something like
POST /users/:id/reset_password
But that means that almost for each modification I could create a different endpoint according to the meaning of the modification, i.e
POST /users/:id/enable
POST /users/:id/birthday
...
or even
GET /user/:id/birthday
compared to simply
GET /users/:id
So basically I don't understand when to stop using a single POST/GET and creating instead different endpoints.
It looks to me as a simple matter of choice, I just want to know if there is some standard way of doing this or some guideline. After reading and looking at example I'm still not really sure.
Disclaimer: In a lot of cases, people ask about REST when what they really want is an HTTP compliant RPC design with pretty URLs. In what follows, I'm answering about REST.
In my view this endpoint could by used for a wide array of functions. I would use it to change the user name or profile, but what about ex, resetting a password?
Sure, why not?
I don't understand when to stop using a single POST/GET and creating instead different endpoints.
A really good starting point is Jim Webber's talk Domain Driven Design for RESTful systems.
First key idea - your resources are not your domain model entities. Your REST API is really a facade in front of your domain model, which supports the illusion that you are just a website.
So your resources are analogous to documents that represent information. The URI identifies the document.
Second key idea - that URI is used by clients to cache representations of the resource, so that we don't need to send requests back to the server all the time. Instead, we have built into HTTP a bunch of standard ways for communicating caching meta data from the server to the client.
Critical to that is the rule for cache invalidation: a successful unsafe request invalidates previously cached representations of the same resource (ie, the same URI).
So the general rule is, if the client is going to do something that will modify a resource they have already cached, then we want the modification request to go to that same URI.
Your REST API is a facade to make your domain model look like a web site. So if we think about how we might build a web site to do the same thing, it can give us insights to how we arrange our resources.
So to borrow your example, we might have a web page representation of the user. If we were going to allow the client to modify that page, then we might think through a bunch of use cases (enable, change birthday, change name, reset password). For each of these supported cases, we would have a link to a task-specific form. Each of those forms would have fields allowing the client to describe the change, and a url in the form action to decide where the form gets submitted.
Since what the client is trying to achieve is to modify the profile page itself, we would have each of those forms submit back to the profile page URI, so that the client would know to invalidate the previously cached representations if the request were successful.
So your resource identifiers might look like:
/users/:id
/users/:id/forms/enable
/users/:id/forms/changeName
/users/:id/forms/changeBirthday
/users/:id/forms/resetPassword
Where each of the forms submits its information to /users/:id.
That does mean, in your implementation, you are probably going to end up with a lot of different requests routed to the same handler, and so you may need to disambiguate them there.

REST API user management URIs

I am writing REST APIs in a MEAN application for user management. Although I normally follow best practices for REST APIs, I do have a security concern about exposing too much detail for user accounts API in the URI.
I would prefer not to include the username or account ID as part of the URI when trying to access a specific user account resource:
/api/accounts/:id or /api/accounts/:username
The one alternate approach I have come across is the use of "me" instead of the resource id:
/api/accounts/me
Most of the use cases I have seen only use GET, but I would like to use this for PUT/POST operations as well:
PUT /api/accounts/me/password
{"oldPassword":"xxx", "newPassword":"yyy"}
Do you think this is a good way? Any other ideas?

Restful principles - sending user's identifier in HTTP headers

I'm creating restful api that is used by angular web page. I'm using token based authentication. Server side determines which user sent request based on token value, so I don't have to pass user id on URI. For example, request that returns all orders for logged (with token) user looks like this:
/api/orders
instead of:
/api/users/123/orders
Api is still stateless, but the same URI returns different data depending on headers. Is it consistent with Restful principles?
I think that this suggested API violates the address-ability feature of REST. The address of a resource should be in a form that is visible and readable (and some other things not related to your question...). One of the nice things of nice URIs is that one can link to it easily. Headers are actually hiding the real address of the resource hence making it impossible to link to it. So bottom line I would not go for such an API.

RESTFul API endpoint design with filtering and authorization

I am designing a REST API with consumers that have different permissions. I understand that a representation of a resource should not change according to user. Therefore I am trying to determine which is the best approach:
GET - list collection of all documents - admin only.:
/api/documents
GET - list collection of all documents - any user with access to document 123
/api/documents/123
For normal users therefore should the endpoints be
list all documents for user 12
/api/user/12/documents
document 123 assuming user 12 has access
/api/documents/123
OR... should the end points be as below and a query string filter used:
/api/documents?user=12
/api/documents/123
In this case you can get away with just two endpoints (and one header!). Make sure the API for /documents is returning the Vary: Authorization header. Then you can use
GET /api/documents // return all docs the logged-in user can see
GET /api/documents?userId=bob // return all of bob's docs that the logged-in user can see
GET /api/documents/123 // return doc 123 if the logged-in user can see it
It is not entirely unreasonable to nest the user a la GET /api/users/bob/documents. I find it to be harder for end users to learn APIs with a large number of endpoints, and I feel that the nested approach tends to create many endpoints. It's conceptually easier to go to /documents and see what you can filter on, rather than look at each endpoint and see what filters it has.
I would keep business logic and authorization logic entirely separate. If you want to retrieve document XYZ, you wouldn't pass the user id as an HTTP parameter.
You suggested /api/documents?user=12 but in fact it should just be /api/documents. The user information should come from the authentication layer.
Similarly authorization should be entirely separate. The reasons for that are:
separation of concern
ability to update authorization logic independently of of business logic
avoid impact on API design
The API should only reflect those business objects you care about e.g. documents in this case (possibly also users should you wish to display a user profile...).
To handle authentication, use the container's standard techniques (e.g. HTTP Basic authentication) or use advanced authentication techniques (OAuth..) via a dedicated framework.
To handle authorization, use a filter, an interceptor. In the Java world (where JAX-RS implements REST), have a look at the Jersey interceptors and filters. You then want the interceptor (or policy enforcement point - PEP) to query an external authorization service (or policy decision point).
Have a further look at ABAC, the attribute-based access control model, and XACML, the eXtensible Access Control Markup Language which explain how to control access to your REST APIs without mixing business logic and authorization logic.