To exchange data between our standalone frontend application and the backend API, we currently have a REST API, with standard endpoint to list/create/update/destroy ressources with a consistent naming and appropriate routes e.g for users
:
GET /api/v1/users: list all users
GET /api/v1/users/{id}: return a specific user
POST /api/v1/users: create a user
PATCH /api/v1/users/{id}: update a user
DELETE /api/v1/users/{id}: destroy a user
However, our platform being a data processing tool, users can choose to start a task applying a certain operation to their data. The frontend will send a request to the backend in order to trigger the background job.
How should this fit in a REST API ? A background task is not a ressource as users
or companies
can be.
I have trouble finding a way to design a good API around launching background tasks or triggering events/messages that are not considered ressources.
How would you approach this ?
Best Answer
Fielding, when defining REST, offered this definition of a resource:
The fact that the underlying implementation is somehow different isn't relevant; on the contrary, part of the point of REST is that the facade insulates the client from the implementation details which might distinguish one resource from another.
How would you
start a task
on a website? Presumably, there would be a link that clients could follow, which would lead to a resource that supported representation of a form; the form would describe the information required of the client as input fields. When the user submitted the form, the browser would use the form processing rules in the HTML specification to compose the request, using as a target uri whatever value was provided in the metadata of the form."Start a task" sounds like it wants unsafe semantics (you probably wouldn't want web spiders coming around starting tasks), so the form metadata would probably specify that the POST method be used.
The web client is just going to copy the form action into the HTTP request without examining or modifying it -- it is fundamentally opaque. So the server can use whatever identifier it wants for the form resource.
We might want "read your own writes", semantics; so if there were a resource that provided a "Most recent tasks" list, that would be a fine candidate for the target of the form, because generic HTTP compliant components will know to invalidate cached representations of a resource when the response includes a non-error status code.
The machines don't care which URI spelling conventions we use; but if we wanted identifiers that people can interpret (sometimes referred to as hackable URI), then we might have
If you wanted to be more specific -- for instance, the most recent tasks for a particular user, you might instead do
/users/{id}/mostRecentTasks /users/{id}/newTaskForm
Where each user would have a form that submits requests to their own task list.
With that idea in mind; there's no rule that says you need to use POST. You could instead allow clients to use their favorite HTTP aware document editor to manipulate the
mostRecentTasks
representations directly, and send you a in turn a complete representation of their local copy (PUT), or a representation of the edits that they have made locally (PATCH).