Skip to main content
POST
Submit a workflow for execution

Authorizations

Authorization
string
header
required

Authorization: Bearer <credential>. The credential is one of: an account-scoped API key (comfyui-…), accepted on Cloud and serverless; a Comfy Cloud session JWT; or an OAuth access token issued for the Comfy Cloud resource. Which kinds a given deployment accepts is deployment configuration — an API key always works on Cloud and serverless, and a deployment that does not accept JWT bearers answers 401 with a message saying so. Self-hosted accepts unauthenticated requests by default and can be configured with a static bearer token.

Headers

Idempotency-Key
string

Client-generated UUID (recommended). Single-use: the first request to present a key is processed; any later request with the same key is rejected 422 idempotency_key_reuse (reject-on-duplicate, no response replay). Keys expire after 24h.

Body

application/json
workflow
object
required

API-format workflow graph, verbatim.

extra_data
object

Per-prompt ComfyUI extra_data, same shape as Comfy Cloud and local ComfyUI. Closed object: only the enumerated keys are accepted, keeping the contract fully typed. Forwarded to the worker per-prompt and excluded from idempotency comparison. On a deployment it is dispatch-only and never stored; on Comfy Cloud it is persisted with the prompt, because the worker needs it, and redacted on every path that returns a workflow to a caller.

Send the one credential you hold: an API key as api_key_comfy_org, or the session token an interactively signed-in client has instead as auth_token_comfy_org. Sending both is accepted and both are forwarded, but it is not a supported combination and which one a node uses is not defined here. Note a session token is short-lived and is not re-minted for you, so one submitted long before it executes may expire in the queue.

Response

Job created and queued.

One execution of a workflow. Durable from creation until expires_at; outputs populates incrementally during execution.

id
string
required
Example:

"7f3d2c1b-9a8e-4d6f-b012-3c4d5e6f7a8b"

status
enum<string>
required

Lifecycle: queued → running → succeeded | failed | expired; a cancel request, or the deletion of the deployment the job is running on, moves running → canceling → canceled. Terminal states: succeeded, canceled, failed, expired.

Available options:
queued,
running,
succeeded,
canceling,
canceled,
failed,
expired
created_at
string<date-time>
required
started_at
string<date-time> | null
required
completed_at
string<date-time> | null
required
expires_at
string<date-time>
required

Retention deadline — a platform property, not an API constant.

queue_position
integer | null
required
progress
object | null
required

The latest progress snapshot; same data the SSE stream pushes.

outputs
object[]
required
error
object | null
required

Execution failure detail, carried in job.error (not an HTTP error).

urls
object
required

Embedded follow-up links — follow these, don't build URLs. A link is either an absolute URL or a host-relative reference (leading /) that already includes any prefix the serving surface is mounted under (e.g. a serverless gateway's /deployment/{deployment_id}/api/v2). Clients MUST resolve a host-relative link against the request origin (scheme + authority), never against a configured base URL — joining it to a base URL that carries the same mount prefix duplicates the prefix.

metrics
object

Values are nullable (a metric not yet available — e.g. execution_ms before a job starts running — is null, not omitted); the example below is deliberately all-non-null purely to work around a Spectral/nimma lint-tooling crash on a literal null inside a schema example combined with additionalProperties.nullable: true — the schema itself is unchanged and still allows null values at runtime.

Example:
deployment_id
string

The deployment the job was sent to: the id in the address it was posted at, which stays the same when the deployment moves to another release. Absent on a surface that runs jobs on no deployment.

Example:

"dep-0f19a2b3c4d5"

release_id
string

The release of the deployment's build that ran the job, which can differ from the release the deployment runs now. Absent where the serving surface does not report it.

Example:

"7c1e9a40-3b2d-4f6a-9e81-0c5d2a7b4f13"