Response envelope
Every v1 response — success or failure — shares one JSON shape. A successful call returns its resource under data; a failed call returns an error object carrying a canonical code and a human-readable message. Field names are snake_case on the wire (the TypeScript SDK renames a few to camelCase for you — see the SDK snippets).
{
"error": {
"code": "rate_limited",
"message": "Too many requests.",
"retry_after_s": 4
}
}{
"error": {
"code": "wrong_region",
"message": "This organization's data lives in a different region.",
"base_url": "https://eu1.wextl.com",
"region": "eu"
}
}Canonical error codes
Every error.code value a shipped v1 route or MCP tool can return, and what it means. Casing is deliberate and NOT uniform: a handful of public-surface-specific codes (rate_limited, wrong_region, workflow_active, workflow_not_deployed, workflow_modified) are lower_snake_case; everything else is UPPER_SNAKE_CASE. Match the exact string — unauthorized and UNAUTHENTICATED are not the same value.
UNAUTHENTICATED(401) — missing or invalid bearer token.FORBIDDEN(403) — the token's scopes don't cover this action — see the scope model in Authentication & scopes.PLAN_FEATURE_DISABLED(403) — the organization's plan doesn't include API access — returned on EVERY call until the org upgrades. The most common first-call failure.PLAN_LIMIT_EXCEEDED(403) — the organization has reached a plan-tier limit (e.g. active workflow count).PAYMENT_REQUIRED(402) — a payment is required before this organization can continue.rate_limited(429) — back off forretry_after_sseconds before retrying — see Rate limits below.wrong_region(421) — retry against thebase_urlin the error payload; see Regions & base URLs.VALIDATION_ERROR(400) — the request body failed validation — seemessage(andfield/fieldswhen present) for detail.INVALID_JSON(400) — the request body was not valid JSON.PAYLOAD_TOO_LARGE(413) — the request body exceeded the size limit.NOT_FOUND(404) — the resource doesn't exist or isn't visible to this token's scopes.CONFLICT(409) — the request conflicts with the resource's current state — refresh and retry.workflow_active(409) — refuses to delete a currently-active workflow — deactivate it first.workflow_not_deployed(404) — requested?view=deployedon a workflow that has never been deployed.workflow_modified(409) — the workflow changed since theexpectedUpdatedAtyou sent was read — re-fetch and retry with the new value.CONCURRENCY_LIMIT(429) — the organization has reached its concurrent-run cap — wait for a run to finish before starting another.ORG_RELOCATING(503) — the organization's data is briefly unavailable while it relocates between regions — retry shortly.INTERNAL(500) — an unexpected server error.
Cursor pagination
List endpoints return a next_cursor field (the TypeScript SDK exposes this as nextCursor) when more results are available. Pass it back as a cursor query parameter to fetch the next page — do not assume offset-based paging or a fixed page count. next_cursor is null on the last page.
Rate limits by plan
Rate limits are per-key AND per-organization (an org-wide bucket sums across every key/OAuth grant in the org, so splitting one integration across several keys never raises the effective ceiling), and scale with your plan's API rate tier. A 429 response always carries retry_after_s in the body and a matching Retry-After header.
Base per-key limits (tier starter, 1×) — multiplied by your plan's tier before enforcement:
read— 600/min. Discover/list/get/validate/resolve calls — the read-heavy majority of an agent's tool-call loop.mutation— 60/min. Graph verbs,create_workflow, schedule/active toggles, credentials, webhooks, databases DDL.mcp— 120/min. The/api/mcptools/call envelope — MCP is stateless one-call-per-request, andinitialize/tools/listcount against this too.run_start— 30/min. Starting a run specifically (start_runand REST run-start), isolated from the broadermutationbucket.envelope— 600/min. A per-key ceiling over ALL calls regardless of class — the backstop for/api/v1, which has no separate class-agnostic cap otherwise.- Org-aggregate — 3× the per-key ceiling above, summed across every key/grant in the organization.
starter 1× (base numbers above)
growth 2×
pro 4×
enterprise 8×References
- WEXTL® error envelope and rate-limit implementation.
- Our users' real error and retry patterns.
- The machine-readable OpenAPI error schema.