LLM-readable documentation index

Errors and Status Codes

How bem reports failures, how to retry safely, and how to handle partial successes

Hand off to an LLM

bem distinguishes two kinds of failure: request errors, returned synchronously when the API can't accept your call, and execution errors, which appear inside otherwise-successful workflow calls when one or more nodes fail. Both shapes are stable — your error-handling code only needs to know two things.

HTTP status codes

CodeMeaningWhen you'll see it
200 OKSuccess, body returnedMost reads; wait=true calls that completed
202 AcceptedAccepted for async processingWorkflow calls without wait=true; eval queueing; collection item ingest
204 No ContentSuccess, no bodyDeletes
207 Multi-StatusPartial successBatch updates where some items succeeded and some failed (e.g. update-transformation)
400 Bad RequestInvalid requestSchema violation, unsupported inputType, malformed outputSchema, contradictory filters
401 UnauthorizedMissing or invalid API keyThe x-api-key header is missing, malformed, or revoked
404 Not FoundResource doesn't existWrong functionName/workflowName/callID, or you're targeting a different environment
422 Unprocessable EntityRequest shape valid, semantics notBody parses but violates a model constraint (e.g. workflow mainNodeName not in nodes)
429 Too Many RequestsRate limit exceededBack off and retry
500 Internal Server ErrorServer-side failureTreat as retryable with backoff; if persistent, contact support with the response body

Request-error shape

Every non-2xx response uses the same body schema:

{
  "message": "human-readable description",
  "code": 400,
  "details": { "field": "outputSchema", "reason": "..." }
}
FieldTypeNotes
messagestringAlways present. Safe to surface to operators; not necessarily safe to surface to end users (may include resource names).
codeintegerOptional. Mirrors the HTTP status when present.
detailsobjectOptional, free-form. Carries field-level context for 400/422 responses; absent for most 500s.

Treat the body as advisory and the HTTP status as authoritative. Don't switch on details.field strings — they're meant for humans, not parsers.

Execution errors inside workflow calls

When a workflow call partially or fully fails, the HTTP response is still 200 (or 202 if you didn't pass wait=true). The failure information lives inside the call object:

{
  "call": {
    "callID": "wc_abc123",
    "status": "failed",
    "outputs": [
      { "eventID": "ev_001", "eventType": "transform", "transformation": { ... } }
    ],
    "errors": [
      {
        "eventID": "ev_002",
        "functionCallID": "fc_abc",
        "workflowNodeName": "invoice-extractor",
        "errorMessage": "outputSchema constraint violation: field 'totalAmount' is required",
        "createdAt": "2024-04-25T19:14:02Z"
      }
    ],
    "url": "/v3/calls/wc_abc123",
    "traceUrl": "/v3/calls/wc_abc123/trace"
  }
}

Two things to note:

  1. outputs and errors are not mutually exclusive. A workflow with three nodes can emit two terminal outputs and one error. Always check both.
  2. call.status reflects the worst outcome. It's completed only if every terminal node produced a non-error event. Any error event flips it to failed. For per-node detail, fetch the trace at traceUrl.

Retry guidance

StatusRetry?How
429YesHonour Retry-After if present, otherwise exponential backoff starting around 1s, capping near 10s.
500/502/503/504YesExponential backoff with jitter, max 5 attempts.
408YesSame as 5xx.
400/401/404/422NoThe request itself needs to change; retrying as-is won't help.
409SometimesWhen returned on a workflow create with a name collision, treat as terminal.

Idempotency

bem uses callReferenceID (on workflow calls) as your deduplication key. Submitting the same callReferenceID for the same workflow within a short window returns the existing call instead of creating a new one — safe to retry network failures without producing duplicates.

For all other operations (function/workflow create + update), use the response's stable IDs (functionID, workflowID) to detect whether your retry succeeded after a network blip.

Common errors and what they mean

Message fragmentWhat it meansFix
outputSchema constraint violationExtracted JSON doesn't satisfy your outputSchema (usually a missing required field)Surface as a workflow output error, not a 4xx — see call.errors[].errorMessage. Tighten upstream prompts or relax the requirement.
unsupported inputTypeThe inputType you sent isn't in the supported listSee Supported file types.
function name already existsYou called create with a name that's already in use in this environmentEither update the existing function or pick a new name.
workflow mainNodeName must be one of nodes[].nameTopology mismatchFix the request body.
BadRequestError: model state limit exceededThe outputSchema is too large/complex for the underlying modelSee Known limitations. Split the schema or reduce nesting.

Observing errors after the fact

The /v3/errors endpoint lists terminal error events across calls and is the right place to power monitoring dashboards or alerts. Filter by workflowNames, functionNames, or callIDs to scope to a specific surface.

On this page