Errors
Every non-2xx response uses the same JSON shape:
{
"error": "Key authenticated but is missing the required scope.",
"code": "scope_missing",
"requiredScope": "workbench:flows:run"
}
error— a human-readable message. Don't branch on it; it's allowed to change for clarity.code— a stable, machine-readable identifier. Switch on this. The set is closed and additive: new codes get added, existing ones are never renamed.- Some codes carry extra fields alongside
error/code—requiredScopeon a scope error,retryAfterSecondson a rate limit,details(e.g. validation issues) on others.
The codes
| Status | code | When |
|---|---|---|
400 | validation | The request is malformed — a bad param, body, or query. details may list the offending fields. |
400 | workspace_required | A personal token call didn't resolve a workspace (no default set, none passed). |
401 | auth_missing | No Authorization: Bearer … header. |
401 | auth_invalid | Unknown key, wrong secret, or revoked. All three funnel into the same response. |
402 | plan_limit | A spend or count limit was reached — a key's cost cap, the workspace's inference balance, or a per-plan count cap. |
402 | plan_gate | The feature isn't included on the workspace's plan. Upgrade to use it. |
403 | scope_missing | Authenticated, but the credential lacks the route's scope. requiredScope names it. |
403 | forbidden | Authenticated, but the credential isn't allowed here — e.g. a personal key on a route that only accepts a workspace key. |
403 | workspace_suspended | The workspace this credential belongs to is temporarily unavailable. Contact support. |
404 | not_found | The resource doesn't exist, or isn't visible to this credential. The response is the same either way. |
404 | flow_not_published | A pinned revision or published version doesn't exist for the flow. |
409 | conflict | The request conflicts with current state — e.g. an idempotency key reused with a different body, or an archived eval. |
429 | rate_limited | A request rate limit tripped. Honor Retry-After. |
504 | timeout | A run exceeded its timeoutMs ceiling. A partial timeline may be in details. |
503 | service_unavailable | A required upstream dependency is temporarily unavailable. Retry with backoff. |
500 | internal_error | Something went wrong on our side. Safe to retry with exponential backoff. |
Endpoints add a few of their own codes within this set — those are listed on each endpoint's reference page.
3 min read