Skip to main content

Errors and Recovery

Check both the HTTP status and response body. The REST API does not use a single error envelope for every failure. An accepted message or task means it was stored or submitted; it does not mean the agent finished its work.

Supported REST routes can select versioned error codes and recovery actions with X-API-Contract: 2026-10-14. The examples below also describe legacy bodies; MCP, SCIM, webhook ingress and dedicated security endpoints retain their separate protocol envelopes.

REST errors​

403 application_request_scope_required means an agent-wide timeline/debug/wait or filespace read/reuse would include foreign, transferred or purged application history. Use principal-scoped application request routes. A known message/file ID, management scope or staff targeting does not bypass this boundary; MCP returns a structured tool error for broad reads and an inaccessible-resource error for unauthorized attachment bytes.

StatusMeaningClient action
400Invalid fields, query parameters, schedule, contact configuration, or request shapeCorrect the input. Field names often map to arrays of messages.
401External Security Halt service authentication failedCheck the dedicated bearer credential, HTTPS, and whether the API is enabled for the Organization. See External Security Halt.
403Missing/invalid Agent REST API key, inactive principal, personal API eligibility, missing scope or security permission, or disallowed senderCheck the error body, credential owner, permissions, and communication policy. Retrying unchanged will not fix it.
404Unknown, archived, or inaccessible resourceVerify the ID and key's owner scope. Archived agents require the archive/restore routes.
409Inactive agent, archive name conflict, incompatible task/action state, stale outbox version, or idempotency conflictFetch current state and reconcile before retrying. An idempotency conflict requires inspecting the original request.
405Unsupported HTTP methodUse the documented method. Remote MCP has no standalone GET event stream.
413External Security Halt request body exceeds 16 KiBReduce the JSON body and keep its fields within the documented limits.
415Unsupported request content type on a DRF endpointSend JSON with Content-Type: application/json.
500Unexpected server failureRecord error_id, time, method, and path; retry only when the operation can be replayed safely.

Deployment proxies can return their own errors, including 429 or non-JSON error pages. Honor Retry-After when present. With default-off API_ADMISSION_ENABLED enabled, metered REST/MCP traffic shares deployment-configurable quotas, concurrent-wait and queued-input bounds. Successful metered requests publish RateLimit-* snapshots; admission rejections use 429 or 503 with Retry-After. See public admission and backpressure. Without that gate, no general request quota or standard rate-limit headers are promised.

Examples of distinct response shapes:

{"schedule": ["Invalid schedule."]}
{
"detail": "API key does not have the required scope.",
"code": "missing_api_key_scope",
"required_scope": "agents:manage"
}
{"detail": "Internal server error.", "error_id": "21d0d060-7977-49c3-ae0b-f11653091f86"}

Validation can also use non_field_errors, a top-level detail, or a top-level list. Do not assume every error has message or a stable code. Missing or invalid Agent REST API keys return 403. External Security Halt uses dedicated bearer credentials and returns 401 for missing, invalid, disabled, revoked, or unavailable credentials, including when the deployment or Organization gate is disabled. Its validation, permission, and event-conflict errors use error and message. Authentication failures use detail and a Bearer challenge; a POST rejected by the locked credential recheck uses error/message without a challenge. SCIM uses its own error envelope and bearer challenge.

Retry decisions​

Browser-task creation and secret replacement can return 503 task_secrets_unavailable when credential encryption is unavailable. No task/secret input is committed by that failed attempt; the response contains no exception or credential material and supplies no readiness interval. Under X-API-Contract: 2026-10-14 the code is in the normal error envelope with action reconcile; legacy mode returns code and detail. Reconcile any earlier uncertain attempt separately. A worker claim that wins over a task-secret edit returns the existing 400 pending-state error. See secret replacement and clearing.

Read requests can normally be retried with bounded exponential backoff and jitter. For writes, use the idempotency matrix: support is operation-specific. An uncertain write can already have succeeded. Covered safe-retry task creation/ingress can use their documented protected key contract; omission or unsupported routes have no replay guarantee.

External Security Halt uses service-identity/event deduplication. A retry must keep the same external_event_id and semantic payload. 409 external_event_id_conflict means that event ID was used for a different request; reconcile the original intervention before submitting another event. Revoking a credential or receiving an authentication error does not release an existing hold.

For an expired or already-resolved pending action, list actions again. For an outbox version conflict, fetch the latest content and obtain a decision on that version. For an inactive agent, activate it intentionally before resending. A successful restore leaves the agent inactive.

Remote MCP errors​

There are three layers to inspect:

  1. An HTTP error such as authentication or origin denial.
  2. A JSON-RPC error object, even with HTTP 200.
  3. A successful JSON-RPC response whose tool result.isError is true.

For example, a business validation failure can return:

{
"jsonrpc": "2.0",
"id": "call-1",
"result": {
"isError": true,
"content": [{"type": "text", "text": "{\"status\":\"error\",\"message\":\"Agent not found.\"}"}],
"structuredContent": {"status": "error", "message": "Agent not found."}
}
}
JSON-RPC codeMeaning
-32700Invalid JSON
-32600Invalid request, unsupported batch shape, or origin rejection
-32601Method not found
-32602Invalid parameters
-32001Mcp-Method or Mcp-Name does not match the body
-32002Resource missing, inaccessible, unavailable, or failed integrity validation

Use tools/list to discover what the key may call. Tool scope failures use structured tool errors. JSON-RPC notifications and responses receive HTTP 202 with no result body. Do not parse that empty response as a failed JSON result.

Extended retry errors​

For gated protected writes, 409 idempotency_conflict means the key already describes different semantics. 400 unsupported_idempotent_wait means remove the explicit wait field before a protected task create. 409 rotation_superseded means a later rotation replaced the original secret; retrieve current metadata. 503 idempotency_unavailable rejects new protected admissions while the gate is off. Existing retained retries still authenticate and recheck authority, and can return ordinary authentication/scope/resource errors. Expired operation lookups return 404. None of these errors authorize blind retries of unknown external effects.

503 idempotent_attachment_storage_unavailable rejects new protected uploads when default or quarantine storage is remote/custom. Use a deployment with local intake; remote prestaging is not available. Retained identical retries remain readable.

Application request recovery​

The gated application adapter requires creation Idempotency-Key and strict bounded inputs. Disabled new admission returns 503/application_requests_disabled; current authority and original ownership still govern reads/replay. Bad/foreign/expired cursors return 400/invalid_cursor, wait capacity returns 429/wait_capacity_exceeded with Retry-After: 1, and bounded database snapshot failure returns 503/wait_state_unavailable. Purged replay content returns 404/original_response_not_retained, while detail retains permitted outcome metadata. Holds and unknown execution settlement are request state observations, not transport errors or proof of task failure. See Application Requests.

Admission errors​

When general admission is enabled, HTTP 429 uses code: request_quota_exceeded or wait_capacity_exceeded; HTTP 503 uses admission_unavailable or work_capacity_exceeded. Honor Retry-After and retry the same protected-write key/body. A rejected new submission has no newly accepted input; a prior accepted attempt may still exist, so reconcile/replay its original ID/key. HTTP quota also applies to accepted replay. Saturation is distinct from failure of accepted execution. See capacity coverage and defaults.

MCP admission failures use the same HTTP statuses and header with JSON-RPC error.code: -32003, the incoming request ID, and machine fields in error.data. They are transport admission failures; ordinary tool/business errors still use result.isError. Inspect both layers. MCP browser CORS exposes retry and rate headers.

Conditional setup/schedule writes return 412 configuration_revision_conflict for a stale ETag, 428 configuration_revision_required for missing If-Match, 400 idempotency_key_required for a missing retry key and 503 configuration_unavailable when new admission is disabled. Correct input or retrieve current state; a fresh retry key with stale configuration never applies.

Typed result outcomes​

New typed admission can return 503 structured_results_disabled. Unsupported/invalid/bounded schemas return a 400 result_schema field error with safe codes unsupported_schema, invalid_schema, schema_bounds or invalid_json, before accepted input. Changed live retry semantics return 409. Result validation/generation/no-result outcomes are request metadata, not HTTP task-success errors: inspect result.state and result.error_code. schema_mismatch, result_bounds and generation_not_completed include no raw model output. Authorized result retrieval returns availability explicitly; ordinary foreign/revoked requests remain inaccessible. See structured results.

Versioned REST errors and HTTP correlation​

All application HTTP responses now carry a generated UUID X-Request-ID. Supply an optional canonical UUID X-Client-Correlation-ID to correlate your own call; only valid 36-character UUIDs are echoed. A supplied X-Request-ID never replaces the server ID. These identify this synchronous exchange and its logs, independently of client_reference, application request IDs, JSON-RPC IDs, setup request IDs and idempotency keys. They do not establish historical worker or provider lineage. Proxies can still return their own responses.

Select X-API-Contract: 2026-10-14 on ordinary REST agent/browser-task, setup/schedule, operation, application-request, event, file and usage/audit resource routes to receive the following representation on HTTP failures. Existing status codes, Bearer challenges and Retry-After remain unchanged. Without the header, existing bodies, including top-level validation lists, remain available. Unknown versions reject before mutation. Utility/webhook ingress, MCP, SCIM and dedicated security routes keep their protocol-specific bodies.

{
"error": {
"code": "configuration_revision_conflict",
"request_id": "3313329d-de42-4945-aeb4-215f3427e818",
"action": "refresh_state",
"field_codes": {},
"details": {"code": "configuration_revision_conflict", "detail": "Configuration changed. Reload before writing."}
}
}

details retains bounded field-map/list structure with credential URLs, private material and reflected submitted strings redacted. field_codes follows the original nested structure, including top-level lists; unknown_field, read_only_field and create_only_field are independent of English messages. Existing explicit domain codes take priority. Generic codes include invalid_input, authentication_required, authentication_failed, permission_denied, resource_not_found, method_not_allowed, unsupported_media_type, conflict, gone, request_too_large, throttled, unavailable and internal_error. New protocol/domain codes may be added; handle unfamiliar ones using HTTP status and reconciliation.

ActionClient behavior
correct_inputCorrect fields, content type, contract or required headers.
reauthenticateRepair credentials or complete the documented SSO/browser flow. Agent REST missing/invalid keys still use 403.
remediate_permissionsRepair current scope, grants, issuer eligibility or policy through an authorized administrator.
refresh_stateFetch current configuration, reconcile changes, then deliberately submit with its ETag and a new operation key.
retry_readRetry the read with bounded backoff/jitter, honoring Retry-After.
retry_same_operationAdmission was rejected before new input on a covered protected write; retain the original operation identity/body and honor Retry-After. Unsupported/unprotected writes use reconcile. Prior acceptance may still exist.
reconcileCheck durable state/original acceptance before retrying. Unsupported writes or uncertain external effects have no automatic safe retry guarantee.

A rollout gate returning 503 is not a promise that the service will recover in a fixed interval. Genuine transient read faults can be retried; arbitrary 5xx writes require reconciliation. Accepted/held work and unknown external effects remain resource states, including successful HTTP acceptances and MCP tool results, rather than invented transport failures.

Versioned details redact reflected values before applying string bounds, preventing a long rejected value's prefix from surviving truncation. Credential-bearing field names are masked in details and field-code maps; machine-code values and ordinary declared field names remain stable.