Errors

Every error response is JSON with ok: false and an error message. Stage failures and sealed deny or halt outcomes get a 422 with the failing stage named explicitly.

Error envelope

{
  "ok": false,
  "duration_ms": 12,
  "error": "human-readable message",
  "error_stage": "DOG"
}

Input-validation errors (HTTP 400) carry only ok and error. error_stage is populated for stage errors and for sealed deny or halt responses. It names the pipeline stage or governance gate that stopped the run:

DOG  PEPG  PROGRAM  DTL  DKEC  CCV  MACC  AIVP_T4  HARDWARE  AER  TOK  DSC
NREP  ZKSP  PHASE4  LEDGER  REGISTRY  DLA  BUNDLE_ANCHOR  PEPG_ADMISSION

PHASE4 is the proof and state binding stage (stage 6). BUNDLE_ANCHOR is the complete-record anchor written after the pipeline finishes. PEPG_ADMISSION is the attestation-gap check that runs before the pipeline.

Governance gates:

  • PEPG, Pre-Execution Policy Gate denied the request (stage 1.5, after DOG). Response includes a sealed deny_receipt and the partial_manifest. No kernel executed.
  • CCV, Continuous Constraint Verification found a per-run budget breach at the post-DKEC boundary. The consumption it counts is caller-declared (request_substance.cost.total_tokens; none reported counts as zero). Response includes a sealed ccv_halt_receipt and the partial_manifest.
  • MACC, Multi-Agent Coordination Constraint found the budget bucket's cumulative caller-declared consumption over its limit (stage 3.6, after DKEC and CCV, before AER). From run 247 on, the bucket is the authenticated API key. Response includes a sealed macc_halt_receipt and the partial_manifest. The kernels had already executed; the AER and every later stage did not run.
  • AIVP_T4, Tier-4 governance refused to release the AI output (stage 3.7). Response includes a sealed aivp_t4_halt_receipt and the partial_manifest.
  • PEPG_ADMISSION, the active policy requires attested fields the caller did not declare. Response includes a sealed attestation_gap_receipt. The pipeline did not run. The hosted API's built-in policy requires no attested fields, so the hosted API does not currently return this.

Status codes

CodeWhenCaller action
200Run completed (ok: true)Read the manifest
400Malformed JSON, missing required field, bad hexFix the request
401Missing or invalid X-Verdifax-Key (once any key has been created, revoked or not)Provide a valid key
404Run id not found, or not visible to the caller's keyConfirm the id and the key
422Sealed deny or halt (PEPG, CCV, MACC, AIVP_T4, PEPG_ADMISSION), or a stage errorRead error_stage; fetch the sealed receipt if one is included
429Rate limit exceeded (per-key)Retry after the Retry-After header
500Unhandled internal errorReport to the operator with the error message, the endpoint, the time of the call and the run_id if one was returned

Stage errors vs. sealed halt outcomes

Both return HTTP 422 with ok: false. The difference is whether a sealed receipt exists.

Sealed deny and halt outcomes (policy or budget decision, sealed artifact):

  • PEPG, The policy denied the request. On the hosted API, whose only rule admits every request, this is a Malicious Code Defense signature match (decision_reason_code MCD_SIGNATURE_MATCH). deny_receipt included.
  • CCV, Per-run budget breached at the post-DKEC boundary. ccv_halt_receipt included, partial manifest sealed.
  • MACC, Cumulative budget exceeded. macc_halt_receipt included, partial manifest sealed.
  • AIVP_T4, Tier-4 governance refused release. aivp_t4_halt_receipt included, partial manifest sealed.
  • PEPG_ADMISSION, Required attested fields missing. attestation_gap_receipt included.

Stage errors (pipeline failure, unsealed):

When a pipeline stage fails (e.g., DOG envelope parsing fails, DKEC kernel crashes), the orchestrator persists the run with status stage_error and returns HTTP 422 with error_stage set. The run is still visible in /runs and /runs/{id} for forensic review, failures are auditable, not silent.

{
  "ok": false,
  "duration_ms": 3,
  "error": "orchestrator: stage DKEC failed: ...",
  "error_stage": "DKEC"
}

No sealed artifact exists for stage_error runs. The run record itself is the only evidence, and it is not independently verifiable.

Input validation happens before any of this. A request with a bad field (for example, a program_id that is not 64-char hex) gets HTTP 400 and no run is persisted:

{
  "ok": false,
  "error": "program_id must be 64-char hex, got 7 chars"
}

Continue