Errors

The error envelope, HTTP status codes, and machine-readable error codes.

Every error uses one envelope, everywhere:

1{
2 "error": {
3 "code": "RATE_LIMITED",
4 "message": "Rate limit exceeded.",
5 "request_id": "req_01H..."
6 }
7}
  • code — a stable, machine-readable string. Branch your error handling on this, not on the message.
  • message — a human-readable explanation. Safe to log; never contains stack traces, tenant IDs, or internal identifiers.
  • request_id — the same value as the X-Request-Id response header. Include it in support requests.

Correlation

X-Request-Id is returned on every response — success or error. If you supply your own X-Request-Id on the request, it is echoed back so you can correlate across your logs and ours.

HTTP status discipline

StatusWhen
200 OKRead succeeded, or a mutation returned the updated resource.
201 CreatedAn order was created.
204 No ContentAn order was deleted.
400 Bad RequestMalformed JSON, or an unknown field was sent (strict input).
401 UnauthorizedMissing, invalid, expired, or revoked API key.
403 ForbiddenValid key without the required scope, or a blocked source IP.
404 Not FoundResource does not exist or belongs to another tenant (existence is never leaked).
409 ConflictState conflict (e.g. mutating a non-DRAFT order) or an idempotency-key conflict.
422 Unprocessable EntityBody is syntactically valid but semantically invalid.
429 Too Many RequestsRate limit exceeded. See Rate Limits.
402 Payment RequiredOver the monthly credit limit or insufficient balance.
503 Service UnavailableA dependency the launch path needs is unavailable (fail-closed).

Error codes

Common code values and their typical status:

codeStatusMeaning
INVALID_REQUEST400Malformed body or an unknown/unexpected field.
UNAUTHORIZED401Missing, invalid, expired, or revoked key.
INSUFFICIENT_SCOPE403Key lacks the scope for this endpoint.
IP_BLOCKED403Source IP is not on the key’s allowlist.
NOT_FOUND404Resource missing or outside your tenant.
CONFLICT409State conflict — e.g. mutating a non-DRAFT order.
IDEMPOTENCY_CONFLICT409Idempotency key reused with a different request body.
OVER_CREDIT_LIMIT402Launch would exceed the monthly credit pool or balance.
RATE_LIMITED429Too many requests; honor Retry-After.
SERVICE_UNAVAILABLE503A launch-path dependency is down (fail-closed).

A cross-tenant read returns 404, not 403, so the API never reveals whether a resource you can’t access exists.

No tenant IDs, ever

Organization and workspace IDs are derived from your API key and appear in neither requests nor responses — including error responses. Sending an unexpected field such as organization_id is rejected as 400 INVALID_REQUEST.