pub enum ErrorCode {
Show 43 variants
UserCancelled,
ExecutionTimeout,
CheckpointTimeout,
ProviderRateLimit,
ProviderAuth,
ProviderTokenLimit,
ProviderServer,
ProviderServer500,
ProviderBadGateway502,
ProviderServiceUnavailable503,
ProviderGatewayTimeout504,
ProviderNetwork,
ProviderParse,
ProviderOther,
InternalPanic,
InternalDroppedChannel,
InternalDeadlock,
InternalTaskAborted,
InternalOther,
ScriptError,
ScriptDepthExceeded,
PartialRetryExhausted,
AuthorRaise,
ToolBudgetExceeded,
ToolApprovalProtocol,
ToolNoRegistry,
ToolError,
AgentToolsDoubleDispatch,
ConfigMissing,
LoopOutputBudgetExceeded,
LoopMultiCheckpoint,
ContextOverflow,
ContextNativeUnsupported,
ContextCompactionExhausted,
CompactionThresholdInvalid,
CompactorSignature,
CompactionLoopOnly,
StdFormatMissing,
StdFormatSyntax,
StdJsonParse,
StdJsonStringify,
StdRegexInvalid,
Other,
}Expand description
Stable, fine-grained error identifier. Each code maps to exactly one
ErrorKind and carries a default user-facing message. Wire form:
AKRIBES-E-<UPPER-KEBAB> (e.g. AKRIBES-E-PROVIDER-RATE-LIMIT).
Codes are intentionally durable: once published, the wire string and
kind() mapping should not change. Add new variants for new
conditions rather than repurposing old ones; SDKs match on these
strings to drive retry/UI/triage logic.
Variants§
UserCancelled
Explicit user/client cancellation via POST /executions/:id/cancel.
ExecutionTimeout
Server-side execution-budget timeout (AKRIBES_EXECUTION_TIMEOUT).
CheckpointTimeout
on_timeout window on a checkpoint elapsed without a resume.
ProviderRateLimit
Provider returned a 429 / rate-limit / quota-exhausted response.
ProviderAuth
Provider returned 401/403, or an API key was missing / not configured.
ProviderTokenLimit
Provider’s reported context window or max_tokens was exceeded.
ProviderServer
Legacy umbrella for any 5xx — kept for wire backward-compat after
the issue #1296 split. New code should construct one of
[ProviderServer500], [ProviderBadGateway502],
[ProviderServiceUnavailable503], or [ProviderGatewayTimeout504].
Decoding the old AKRIBES-E-PROVIDER-SERVER wire string yields this
variant so SDKs that match on it stay green.
ProviderServer500
Provider returned HTTP 500. Maybe-transient; short retry-with-backoff.
ProviderBadGateway502
Provider returned HTTP 502 (bad gateway). Retry with short backoff.
Provider returned HTTP 503 (service unavailable). Rate-limit-adjacent
— honour Retry-After aggressively.
ProviderGatewayTimeout504
Provider returned HTTP 504 (gateway timeout). Longer base backoff since the slow side is unlikely to recover faster than the request.
ProviderNetwork
Network-level failure reaching the provider (DNS, TLS, reset, per-provider request timeout).
ProviderParse
Provider response did not parse as the expected schema.
ProviderOther
Generic provider/runtime failure that didn’t fit a more specific bucket.
InternalPanic
A spawned engine task panicked (host-side bug).
InternalDroppedChannel
A oneshot::Receiver returned Err because its sender was dropped
before sending — covers breakpoint resume, checkpoint resume,
tool-approval resume. Indicates a server-side cleanup race or a
host bug, never a user action.
InternalDeadlock
Engine reached a state with pending nodes but none ready to run — dependency cycle or compiler bug.
InternalTaskAborted
JoinError that wasn’t a panic and wasn’t a recognized cancel — tokio runtime aborted the task externally. Treated as a host invariant violation.
InternalOther
Generic “this should not happen” host failure that doesn’t fit the more specific Internal* codes.
ScriptError
Generic workflow-author error not categorised more specifically.
ScriptDepthExceeded
Cross-script call(...) chain exceeded the depth cap.
PartialRetryExhausted
Validation retries exhausted with allow_partial: true (issue #202)
— partial-retry sentinel routed to on unable / handler.
AuthorRaise
Workflow author’s fail arm fired — the LLM returned an Unable
or other non-success variant the author mapped to failure.
ToolBudgetExceeded
Per-agent tool budget (tool_budget) exceeded.
ToolApprovalProtocol
Tool approval resume returned a payload that wasn’t the expected
{ approve: bool, args?: Value } shape — host protocol violation.
ToolNoRegistry
Tool call attempted but no MCP registry was attached (script-only engine, missing host wiring).
ToolError
MCP tool call returned a tool-side failure (the registry exists and dispatched, but the tool itself errored).
AgentToolsDoubleDispatch
Agent dispatched a second tool_use after the engine had already
folded one round-trip’s tool results back into the conversation.
Agents are single-round-trip by design — multi-turn agentic
behaviour belongs on a loop block. Surfaces when an LLM ignores
the synthesized “produce your final answer now” follow-up turn
and tries to invoke tools again. The fix is either to use a
loop block or to tighten the agent’s system prompt.
ConfigMissing
Required configuration missing (API key, env var, etc.).
LoopOutputBudgetExceeded
Loop block exceeded its max_total_output_tokens budget. The
loop driver accumulates each turn’s output_tokens from the
provider and stamps this code on the resulting LoopEnd { value: FatalError } once the running total exceeds the per-loop or
project-default cap.
LoopMultiCheckpoint
A second checkpoint fired in the same loop turn. The supported
envelope is at most one checkpoint per turn — the driver tracks a
per-turn counter and fails fast when the increment goes past 1.
Surfacing this as a distinct code (rather than Other) lets SDKs
and the Studio render a targeted explanation: split the
checkpoints across turns, or move one onto a non-loop sibling.
ContextOverflow
Mode 1 (compaction: none / omitted) only — the assembled
request would exceed the model’s context window. Pre-call
diagnostic emitted by Engine::run_compaction_chain; replaces
the cryptic provider 400 from upstream. Carries the conversation
length, the model cap, and the agent in the message body.
ContextNativeUnsupported
compaction: native() (or at <T>: native()) used with a model
whose ModelEntry::native_compaction_capable is false. The
related-info span points at the model declaration.
ContextCompactionExhausted
All custom-chain steps ran and the conversation still exceeds the configured cap. Surfaces with the chain of attempted strategies in the message body. Emitted instead of a provider 400 — fail-fast at the akribes seam.
CompactionThresholdInvalid
compaction: at <invalid> — value <= 0, percent > 100, or
duplicate threshold in a custom chain. Compile-time only.
CompactorSignature
User-defined compactor task referenced from a compaction step
doesn’t match one of the four supported signatures
(str|list[message] -> str|list[message]). Compile-time only.
CompactionLoopOnly
compact_to_state(field=...) used outside a loop’s compaction:
block. The primitive is loop-only because it writes into the
loop’s state record. Compile-time only.
StdFormatMissing
std.format placeholder {name} not present in args.
Stable string form: AKRIBES-E-STD-FORMAT-MISS-001 (#1224).
StdFormatSyntax
std.format malformed template (unclosed {, empty {},
stray }). Stable string form: AKRIBES-E-STD-FORMAT-SYNTAX-001.
StdJsonParse
std.json_parse could not parse the input string as JSON.
Stable string form: AKRIBES-E-STD-JSON-PARSE-001.
StdJsonStringify
std.json_stringify could not serialise the input value (e.g.
FatalError payload; non-serializable). Stable string form:
AKRIBES-E-STD-JSON-STRINGIFY-001.
StdRegexInvalid
std.regex_extract was given an invalid regex pattern.
Stable string form: AKRIBES-E-STD-REGEX-001.
Other
Catch-all for sites that haven’t been migrated to a richer code. Prefer adding a specific variant — this is for transition only.
Implementations§
Source§impl ErrorCode
impl ErrorCode
Sourcepub fn parse_retry_after_ms(msg: &str) -> Option<u64>
pub fn parse_retry_after_ms(msg: &str) -> Option<u64>
Extract a retry_after_ms hint from a provider error message
when the wire response carried one (provider implementations
usually echo it as retry-after: <secs> or similar). None when
no such hint is present.
Honours both RFC 9110 §10.2.3 forms:
- delta-seconds —
Retry-After: 30(returned as30_000). - HTTP-date —
Retry-After: Wed, 21 Oct 2026 07:28:00 GMTparsed viahttpdate::parse_http_dateand returned as the delta fromSystemTime::now(), clamped to>= 0.
Source§impl ErrorCode
impl ErrorCode
Sourcepub fn kind(&self) -> ErrorKind
pub fn kind(&self) -> ErrorKind
The ErrorKind bucket this code belongs to. Computed once,
statically — used by consumers that want the rollup behaviour
(is_transient, suggested_action) without hand-mapping codes.
Sourcepub fn as_wire(&self) -> &'static str
pub fn as_wire(&self) -> &'static str
Stable wire identifier (AKRIBES-E-<UPPER-KEBAB>). This is the
string consumers should match on for retry/UI logic.
Sourcepub fn from_wire(s: &str) -> Option<Self>
pub fn from_wire(s: &str) -> Option<Self>
Parse the canonical wire form (AKRIBES-E-<UPPER-KEBAB>) back to a
code. Returns None for any string we don’t recognise so the
caller can decide whether to fall back to ErrorCode::Other
or surface the unknown code as-is. Used by the legacy
Value::fatal_with_code shim and SDK normalisers.
Sourcepub fn default_user_message(&self) -> &'static str
pub fn default_user_message(&self) -> &'static str
Default user-facing message for this code. Constructors should override only when there is meaningfully more to say to the user (e.g. embedding the offending value), not just to restate the developer message.