How to design a REST API that can "prompt" the client about long-running operations?

by meci   Last Updated August 01, 2020 07:05 AM - source

Say you were to develop a REST API that provides access to a set of complex, long-running, operations.

The typical paradigm for an API like this (as I understand it) usually involves (the client) making a request to the server, asking it to perform a given long-running operation. The server will respond with a 202 Accepted message indicating that the request has been received and, with it, provides the location of the result, where it will eventually become available. The client, from then on, polls this location until the result of the long-running task becomes available.

This much makes sense. However, imagine now that these long-running tasks are more complex. Imagine that, during the execution of a task, a specific resource, file, network, etc. becomes unavailable and, in order to proceed, the API must "ask" the client whether the job should continue anyway or whether the task should end here.

How would this requirement change the original paradigm? Instead of having some result located at the given location, would you optionally return some notion of a "question" that needs to be posted back to the server in order to continue?

Assume for the purposes of this question that you can't encode some kind of blanket "continue if error" parameter in the original request and that these questions must be addressed on a case-by-case basis, as they arise, if they arise.

Maybe I'm thinking about this problem the wrong way? I'd be curious to hear how a paradigm like this is usually accomplished, or if it's as simple as, "yeah, just respond with the prompt, post back the result to the server, and continue to query the original location."

I would really appreciate any help I could get.



Answers 1


For long-running operations, it often helps to model the active job as a REST resource with its own structure and/or sub-resources.

For example, starting a job may return a result such as

202 Created
Location: https://example.com/jobs/123

At that URL, the client will get a structure such as

{
  "status":"running"
}

as long as the job is running,

{
  "status":"finished",
  "result":"https://example.com/jobs/123/result"
}

when it is completed and a result is available, or

{
  "status":"interaction-required",
  "prompt":"xyz service not available, please restart it or cancel job.",
  "continue":"https://example.com/jobs/123/continue"
}

to interact with the user. The job would continue (retrying xyz access) after the client posts something to the continue URL, or would be cancelled by using DELETE on the job URL, for example.

The details about which kinds of interaction are possible and how they are presented in the client would need to be designed based on the specific needs of these jobs, but the main thing is that the operation start does not just return the location of the result but of a reified job object that can be queried and manipulated.

Hans-Martin Mosner
Hans-Martin Mosner
August 01, 2020 07:04 AM

Related Questions


Including aggregate data in REST response in DDD

Updated February 16, 2018 11:05 AM