Skip to main content
There is no synchronous endpoint. Driving an AI engine takes seconds to minutes — often in a real browser — so every request becomes a durable queued task that you collect later.

Lifecycle

Statuses

status
Accepted and durable. Waiting for a worker.
status
A worker holds a lease on the task and is driving the engine.
status
Terminal. The response field is populated.
status
Terminal. The error field carries the reason.
Internally the queue stores RUNNING, but the wire contract exposes PROCESSING. This is deliberate — the database enum is internal state, the status you see is the contract.
A task that hits a transient failure (engine timeout, no account available) returns to QUEUED and is retried. Only once retries are exhausted does it settle in FAILED, so PROCESSING → QUEUED transitions are normal and not something to alarm on.

Priority

priority accepts 1 through 10, higher wins. Values outside that range are clamped rather than rejected. Defaults to 1.
Priority orders the queue; it does not reserve capacity. A high-priority task still waits behind whatever is already PROCESSING, and it cannot conjure an account or IP that the engine’s pool does not have.

Retention

Terminal tasks are retained for 24 hours, then swept. After that, GET /v1/async/task/{id} returns 404 NOT_FOUND — the same response as an id that never existed, because the row is gone and the two cases are indistinguishable. If you rely on polling rather than webhooks, collect results well inside that window.

Choosing webhook or polling

Prefer webhooks. Polling is the recovery path. A robust client does both: take the webhook as the fast path, and reconcile anything you never heard about by polling before the retention window closes.