Error Codes
Purpose #
The full map of AidoError.code ↔ exit code ↔ situation. Authoritative source: .docs/docs/specs/cli-reference.md §10.2.
Conventions #
- Codes are
SCREAMING_SNAKE_CASE. - Prefix indicates category:
PREREQ_*,ADAPTER_*,MCP_*,FS_*,MIGRATE_*, … - Codes are stable across releases — new codes added; existing codes never renamed.
Reserved error codes #
| Code | Exit | Category | Meaning |
|---|---|---|---|
BAD_INVOCATION |
2 | invocation | Argument parsing failure |
PREREQ_MISSING |
10 | prereq | Required prerequisite not installed |
PREREQ_VERSION_TOO_LOW |
10 | prereq | Installed but version below minimum |
ADAPTER_NOT_FOUND |
11 | adapter | Adapter package not installed or unresolvable |
ADAPTER_LOAD_FAILED |
11 | adapter | Adapter package failed to import or initialize |
ADAPTER_SPEC_MISMATCH |
11 | adapter | Adapter's spec version differs from CLI's |
STACK_PACK_NOT_FOUND |
12 | stack pack | Stack pack not installed |
CONFORMANCE_FAILED |
13 | conformance | Harness or doctor check failed |
FS_WRITE_FAILED |
20 | filesystem | File write error |
FS_PERMISSION_DENIED |
20 | filesystem | Insufficient permissions |
MCP_INSTALL_FAILED |
21 | MCP | MCP registration command exited non-zero |
MCP_NOT_IN_CATALOG |
21 | MCP | Requested MCP id not in catalog (no --custom-url) |
MIGRATION_FAILED |
30 | migration | Migration script error |
USER_CANCELLED |
40 | user | User declined an interactive prompt |
NETWORK_FAILED |
50 | network | Network operation failed |
OFFLINE |
50 | network | Network needed but AIDO_OFFLINE=1 |
VALIDATION_FAILED |
60 | validation | Artifact failed schema validation |
SYNC_CONFLICT |
70 | conflict | Sync diff has conflicts and user did not resolve |
POLICY_INVALID |
60 | validation | .aidokit/policy.json failed schema validation |
POLICY_READ_FAILED |
20 | filesystem | .aidokit/policy.json could not be read/parsed |
CORRUPT_STATE |
1 | core | Malformed task state (e.g. agent-artifacts/<id>/state.json) |
v1.x finding codes — aidokit verify facets #
These codes are reported by aidokit verify facets. Severity is error unless noted. See ADR-0018.
| Code(s) | Facet | Meaning |
|---|---|---|
SECRET_AWS_ACCESS_KEY, SECRET_AWS_SECRET_KEY, SECRET_GITHUB_PAT, SECRET_SLACK_TOKEN, SECRET_STRIPE_KEY, SECRET_ANTHROPIC_API_KEY, SECRET_OPENAI_API_KEY, SECRET_NPM_TOKEN, SECRET_GCP_SA_JSON, SECRET_JWT, SECRET_SSH_PRIVATE_KEY |
--secrets |
Bundled provider-specific credential patterns matched in scanned content. |
SECRET_HIGH_ENTROPY |
--secrets |
Shannon-entropy fallback hit — possible unknown-format secret. |
BUDGET_EXCEEDED |
--budget |
Computed task spend exceeds policy.budget.maxUsdPerTask. |
BUDGET_NEAR_LIMIT |
--budget |
Within configurable warning threshold of the budget cap. Severity warn. |
BUDGET_LEDGER_MISSING |
--budget |
agent-artifacts/metrics/events.jsonl token ledger absent. |
DEP_NEW_UNAPPROVED |
--deps |
New dependency outside allowedScopes and no justification block. |
DEP_NEW_UNJUSTIFIED |
--deps |
New dependency added without a change-summary ## Dependencies section. |
DEP_VERSION_DOWNGRADE |
--deps |
Dependency version moved backwards. |
LICENSE_HEADER_MISSING |
--license |
SPDX header required (requireHeaders: true) but missing. |
LICENSE_INCOMPATIBLE |
--license |
Detected license incompatible with project license. |
LICENSE_FORBIDDEN |
--license |
Detected license in forbidden list. |
LICENSE_UNKNOWN |
--license |
License could not be resolved. |
LOOP_CAP_EXCEEDED |
--loop-cap |
Task iteration count exceeds policy.loopCap.maxIterations. |
LOOP_CAP_NEAR_LIMIT |
--loop-cap |
Within warning threshold of the loop cap. Severity warn. |
FACET_NOT_IMPLEMENTED |
all | Facet is stubbed (returns deferred-impl signal). |
v1.x finding codes — aidokit doctor #
| Code | Check | Meaning |
|---|---|---|
MCP_QUARANTINE_SKILL_MISSING |
core/MCP | An MCP server marked untrustedOutput: true is enabled without the quarantining-untrusted-output skill present. See ADR-0019. |
MODEL_LOCK_MISSING |
--model-drift |
.aidokit/model.lock absent. |
MODEL_DRIFT_DETECTED |
--model-drift |
Declared adapter cliVersion does not match .aidokit/model.lock. |
HYGIENE_NO_SCRATCHPAD |
--hygiene |
Active task brief references a scratchpad that does not exist. |
HYGIENE_STALE_SCRATCHPAD |
--hygiene |
Scratchpad exists but has not been touched in the freshness window. |
HYGIENE_DRIFT |
--hygiene |
Brief↔commit drift (committed code without a corresponding brief, or vice versa). |
doc-drift |
--drift (semantic) |
Broken file reference or missing symbol reference in docs. Severity warn. |
Exit-code groups #
From .docs/docs/specs/cli-reference.md §8:
| Code | Group |
|---|---|
| 0 | Success |
| 1 | Generic error |
| 2 | Bad invocation |
| 10 | Prereq missing |
| 11 | Adapter |
| 12 | Stack pack |
| 13 | Conformance |
| 20 | Filesystem |
| 21 | MCP |
| 30 | Migration |
| 40 | User |
| 50 | Network |
| 60 | Validation |
| 70 | Conflict |
Envelope shape #
export class AidoError extends Error {
constructor(
public code: string, // e.g. 'PREREQ_MISSING'
message: string, // human-readable
public details?: Record<string, unknown>,
public hint?: string, // suggested fix
) { super(message); }
}
--json mode emits:
{
"ok": false,
"command": "init",
"error": {
"code": "PREREQ_MISSING",
"exitCode": 10,
"message": "Prerequisite missing: Claude Code",
"details": { "prereq": "claude-code", "minVersion": "2.1.32" },
"hint": "Install Claude Code via: curl -fsSL claude.ai/install.sh | bash"
}
}
Human mode formats the same envelope as:
✘ Prerequisite missing: Claude Code (PREREQ_MISSING)
Detected: No `claude` command found on PATH.
Hint: Install Claude Code via:
curl -fsSL claude.ai/install.sh | bash
Or set --skip-prereq-check to bypass.
Adding a new error code #
- Add the constant to
packages/core/src/error.tsErrorCodeconstants. - Map it to an exit code in
packages/cli/src/exit-codes.ts. - Document the new code in this file and in .docs/docs/specs/cli-reference.md §10.2.
- Bump
@aidokit/coreminor (new code is additive).