> ## Documentation Index
> Fetch the complete documentation index at: https://docs.manthan.systems/llms.txt
> Use this file to discover all available pages before exploring further.

# Error Codes

> The canonical code list from the Error Model v1 spec, checked against what's actually thrown

`docs/api/03-error-model.md` ("Error Model v1 (Locked)") defines 24 canonical error codes across six categories. [REST API → Error Model](/docs/api/error-model) already documents that the running server doesn't use this spec's nested `{ "error": { "code", "message" } }` shape at all — it returns a flat `{ "error": string }`, with a top-level `code` attached only for errors that subclass `packages/runtime/src/errors/RuntimeError.ts`'s `RuntimeError`. This page goes one level further: of the 24 specified codes, which ones are actually thrown by any code in `packages/`, and do they reach an HTTP response?

## The canonical list

| Category       | Codes                                                                                                                      |
| -------------- | -------------------------------------------------------------------------------------------------------------------------- |
| Validation     | `INVALID_REQUEST`, `INVALID_METADATA`, `INVALID_POLICY`, `INVALID_SIGNALS`, `INVALID_SCHEMA`                               |
| Authentication | `UNAUTHENTICATED`, `INVALID_TOKEN`, `TOKEN_EXPIRED`                                                                        |
| Authorization  | `FORBIDDEN`, `INSUFFICIENT_PERMISSIONS`                                                                                    |
| Resource       | `BUSINESS_TRANSACTION_NOT_FOUND`, `EXECUTION_NOT_FOUND`, `RECEIPT_NOT_FOUND`, `POLICY_NOT_FOUND`, `VERIFICATION_NOT_FOUND` |
| Conflict       | `DUPLICATE_TRANSACTION`, `OVERRIDE_NOT_ALLOWED`, `IMMUTABLE_RESOURCE`                                                      |
| Verification   | `VERIFICATION_FAILED`, `INVALID_SIGNATURE`, `TRUST_RECORD_CORRUPTED`, `POLICY_MISMATCH`                                    |
| Internal       | `INTERNAL_ERROR`, `STORAGE_FAILURE`, `UNEXPECTED_ERROR`                                                                    |

## What's actually wired up

Searching `packages/` for each literal code string turns up exactly five that appear as the `code` value of a real, constructible error class — all the rest have no corresponding thrown error anywhere in the monorepo today.

| Code                             | Thrown by                                                                                                                                                          | Reaches an HTTP `code` field?                                                                                                                                                                                                                                                                                                                                                                                   |
| -------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `VERIFICATION_FAILED`            | `VerificationFailedError` (`packages/runtime/src/errors/VerificationFailedError.ts`), thrown by `VerificationService.verify()` when the trust record doesn't exist | **Yes.** It extends `RuntimeError`, so `errorHandler`'s `instanceof RuntimeError` branch attaches it: `{ "error": "...", "code": "VERIFICATION_FAILED" }`, status `404`. Reachable via `POST /verify` with an unknown `businessTransactionId`.                                                                                                                                                                  |
| `POLICY_NOT_FOUND`               | `PolicyNotFoundError` in `packages/shared/src/errors/policy-not-found-error.ts` (`code: "POLICY_NOT_FOUND"`, extends `ParmanaError`)                               | **No.** The `PolicyNotFoundError` actually thrown at runtime is a *different* class with the same name in `packages/policy/src/errors/PolicyNotFoundError.ts`, which has no `code` field at all — that's the one `FilePolicyRepository.load()` throws and the one `errorHandler` imports and checks. The `shared` package's version, with the real `POLICY_NOT_FOUND` code, is never thrown anywhere reachable. |
| `BUSINESS_TRANSACTION_NOT_FOUND` | `BusinessTransactionNotFoundError` (`packages/shared/src/errors/business-transaction-not-found-error.ts`), thrown by `ExecutionService.create()`                   | **No.** This class extends `ParmanaError`, not `RuntimeError`, and `errorHandler` doesn't have a specific `instanceof` check for it either — it falls through to the generic `500 { "error": "Internal Server Error" }` branch, logged via `console.error`. A well-formed 404-shaped domain error becomes a generic 500 in the actual HTTP response.                                                            |
| `FORBIDDEN`                      | `ForbiddenError` (`packages/shared/src/errors/forbidden-error.ts`)                                                                                                 | Defined, but not observed to be thrown from any reachable path under `packages/runtime` or `packages/api` in this snapshot — there's no authorization check anywhere yet to trigger it (see [Authentication](/docs/api/authentication)).                                                                                                                                                                        |
| `OVERRIDE_NOT_ALLOWED`           | `OverrideNotAllowedError` (`packages/shared/src/errors/override-not-allowed-error.ts`)                                                                             | Defined, but unreachable in practice: nothing under `packages/api` calls `OverrideService` at all (see [Guides → Human Override](/docs/guides/human-override)), so nothing can trigger this.                                                                                                                                                                                                                    |

The remaining 19 codes — every Validation and Authentication code, `INSUFFICIENT_PERMISSIONS`, `EXECUTION_NOT_FOUND`, `RECEIPT_NOT_FOUND`, `VERIFICATION_NOT_FOUND`, `DUPLICATE_TRANSACTION`, `IMMUTABLE_RESOURCE`, `INVALID_SIGNATURE`, `TRUST_RECORD_CORRUPTED`, `POLICY_MISMATCH`, `INTERNAL_ERROR`, `STORAGE_FAILURE`, `UNEXPECTED_ERROR` — do not appear as the `code` of any error class anywhere under `packages/` in this snapshot. Failures that conceptually match several of these (missing `businessTransactionId`, a not-found trust record, a not-found receipt) are reported today as plain `{ "error": string }` bodies with no `code` at all, directly from the route handler — see the practical status-mapping table in [Error Model](/docs/api/error-model#practical-status-mapping-as-implemented).

<Warning>
  If you're building a client that switches on error `code`, only `VERIFICATION_FAILED` is currently both real and reachable end-to-end. Match on HTTP status and the `error` message string for everything else, exactly as [Error Model → Recommendation for integrators](/docs/api/error-model#recommendation-for-integrators) already advises.
</Warning>

## Related

<CardGroup cols={2}>
  <Card title="Error Model" href="/docs/api/error-model">The full spec-vs-implementation breakdown this page builds on.</Card>
  <Card title="Glossary" href="/docs/reference/glossary">Other normative vocabulary from the specification.</Card>
  <Card title="TypeScript SDK → Errors" href="/docs/typescript-sdk/errors">A parallel, unrelated error hierarchy on the client side.</Card>
  <Card title="Verify" href="/docs/api/verify">Where `VERIFICATION_FAILED` is actually reachable.</Card>
</CardGroup>
