This pattern outlines managing long-running tasks by embedding the task’s status directly within the resource’s representation, allowing clients to receive comprehensive updates in a single request.
Details
Upon initiating a long-running task, the API provides a 202 Accepted status and a Location header pointing to the resource, which includes a status field within its representation. Clients periodically poll this resource to receive status updates and other relevant data.
Common Pattern Names/Synonyms
- Resource State Polling
- Embedded Status Pattern
- Self-Contained Status Pattern
- Status Representation Pattern
Common Use Cases
- Resource Provisioning: Creating a complex resource such as setting up a virtual machine.
- Content Moderation: Submitting content for moderation with trackable status and results.
- Order Processing: Monitoring the processing of orders with details updating in real-time.
When to Use
- Integration of status with data updates: Ideal when updates to the resource and the status are closely linked.
- Fewer API endpoints: Beneficial for minimizing the number of different endpoints by combining data and status.
- Continuous resource monitoring: Suitable for applications needing frequent updates on a resource’s state, but the client is unable to leverage Webhooks and/or is not capable of using Websockets or other server-push notification options.
When Not to Use
- Only status updates are needed: Inefficient if clients do not require additional data beyond the status.
- Highly dynamic status information: May lead to inefficiencies if the status changes very frequently, increasing data transfer unnecessarily.
Examples
Creating a New Resource
Request:
POST /api/virtual-machines HTTP/1.1
Host: example.com
Content-Type: application/json
{
"configuration": {
"os": "Linux",
"ram": "16GB",
"storage": "256GB SSD"
}
}
Response:
HTTP/1.1 202 Accepted
Location: /api/virtual-machines/67890
Polling for Status and Details
Request:
GET /api/virtual-machines/67890 HTTP/1.1
Host: example.com
Response (In Progress):
HTTP/1.1 200 OK
Content-Type: application/json
{
"id": "67890",
"status": "Provisioning",
"configuration": {
"os": "Linux",
"ram": "16GB",
"storage": "256GB SSD"
},
"progress": "50%",
"estimatedTimeRemaining": "15 minutes"
}
Response (Complete):
HTTP/1.1 200 OK
Content-Type: application/json
HTTP/1.1 200 OK
Content-Type: application/json
{
"id": "67890",
"status": "Ready",
"configuration": {
"os": "Linux",
"ram": "16GB",
"storage": "256GB SSD"
},
"IPAddress": "192.168.1.10"
}
Sequence Diagram (queries background job status)
sequenceDiagram participant Client participant Server participant BackgroundProcess as Background Process
Client->>Server: 1. POST /api/virtual-machines
Server->>BackgroundProcess: 2. Initiate Background Process
Server-->>Client: 3. 202 Accepted (Location: /api/virtual-machines/678)
Client->>Server: 4. GET /api/virtual-machines/678
Server->>BackgroundProcess: 5. Query Process Status & Details
Server-->>Client: 6. 200 OK (Status: Provisioning, Config: {...}, Progress: 50%)
Client->>Server: 7. GET /api/virtual-machines/678
Server->>BackgroundProcess: 8. Query Process Status & Details
Server-->>Client: 9. 200 OK (Status: Ready, Config: {...}, IP Address: 192.168.1.10)
Sequence Diagram (API is updated via message to update state)
sequenceDiagram participant Client participant Server participant MessageBroker as Message Broker participant BackgroundProcess as Background Process participant Database
Client->>Server: 1. POST /api/virtual-machines
Server->>BackgroundProcess: 2. Initiate Background Process
Server-->>Client: 3. 202 Accepted (Location: /api/virtual-machines/678)
BackgroundProcess->>MessageBroker: 4. Post Job Completion Status
MessageBroker->>Server: 5. Notify API of Job Completion
Server->>Database: 6. Update Resource Status & Details in DB
Client->>Server: 7. GET /api/virtual-machines/678
Server->>Database: 8. Retrieve Status & Details from DB
Server-->>Client: 9. 200 OK (Status: Ready, Config: {...}, IP Address: 192.168.1.10)
OpenAPI Example
openapi: 3.0.0
info:
title: Embedded Status API
version: 1.0.0
servers:
- url: 'https://api.example.com'
paths:
/virtual-machines/{vmId}:
get:
summary: Retrieves the status and details of a virtual machine
parameters:
- name: vmId
in: path
required: true
schema:
type: string
responses:
'200':
description: Current status and details of the virtual machine
content:
application/json:
schema:
type: object
properties:
id:
type: string
status:
type: string
configuration:
type: object
properties:
os:
type: string
ram:
type: string
storage:
type: string
progress:
type: string
estimatedTimeRemaining:
type: string
examples:
provisioning:
value:
id: "67890"
status: "Provisioning"
configuration:
os: "Linux"
ram: "16GB"
storage: "256GB SSD"
progress: "50%"
estimatedTimeRemaining: "15 minutes"
ready:
value:
id: "67890"
status: "Ready"
configuration:
os: "Linux"
ram: "16GB"
storage: "256GB SSD"
IPAddress: "192.168.1.10"
/virtual-machines:
post:
summary: Creates a new virtual machine
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
configuration:
type: object
properties:
os:
type: string
ram:
type: string
storage:
type: string
examples:
newVM:
value:
configuration:
os: "Linux"
ram: "16GB"
storage: "256GB SSD"
responses:
'202':
description: Virtual machine creation initiated
headers:
Location:
schema:
type: string
description: URI to poll for VM status