# Standards

Source: https://permdock.com/docs/standards

Why PermDock is standards-first and which specification each part of the library implements or targets.

PermDock is an in-process library, not a hosted policy service. It still has to talk to the rest of an authorization stack: identity providers that issue tokens, policy decision points that already exist in an organisation, API gateways that read OpenAPI documents, database engines that enforce row-level security, and agent runtimes (MCP servers, the AI SDK, the Claude Agent SDK, A2A agents, browsers running WebMCP) that need a yes/no/ask answer for every tool call. Every one of those seams already has a specification. PermDock adopts the specification instead of inventing a wire format, a policy language or a token shape of its own.

## Why standards-first [#why-standards-first]

* **Interop with PDPs and PEPs.** The decision endpoint speaks OpenID AuthZEN 1.0, so a Cerbos, Topaz or Keycloak deployment can call PermDock, and the `pdp` provider can call any certified PDP. See [AuthZEN](/docs/standards/authzen).

* **Interop with identity providers.** Subjects carry OAuth scopes and RFC 9396 `authorization_details`; revocation arrives as CAEP events; MCP Enterprise-Managed Authorization tokens are consumed as-is. See [OAuth for agents](/docs/standards/oauth-agent-delegation) and [Shared Signals and CAEP](/docs/standards/shared-signals-caep).

* **Interop with agent runtimes.** Each runtime already has a permission hook (`scopeChallenge`, `toolApproval`, `canUseTool`, Agent Card `securityRequirements`, `document.modelContext.registerTool`). PermDock translates one `Decision` into each vocabulary rather than asking runtimes to learn a new one.

* **Agents can wire PermDock without bespoke formats.** A coding agent that knows Standard Schema, OpenAPI, Problem Details and MCP authorization already knows most of PermDock's surface. Skills, `AGENTS.md` and `llms.txt` follow the same rule. See [Agent docs standards](/docs/standards/agent-docs-standards).

* **Fewer things to get wrong.** Fail-closed defaults, `deny` overriding `allow`, prototype-safe paths and boundary validation are easier to audit when the inputs are well-specified formats rather than free-form objects. See the [threat model](/docs/security/threat-model).

* **Conformance is tested where a machine-readable test exists.** AuthZEN runs the working group's interop vectors through `testAuthZen` ([AuthZEN](/docs/standards/authzen)). `permdock openapi` output is validated in CI against the official OpenAPI 3.1 and 3.2 JSON Schemas and the Overlay 1.1 schema, vendored under `packages/permdock/schemas/openapi`. Draft output (OpenAPI 3.3, Overlay 1.2) has no published schema yet, so only the stable twin shipped next to it is schema-validated. Every page in this section has a test file, `packages/permdock/tests/standards/<slug>.test.ts`, and `pnpm docs:drift` fails when a page or a test lacks its twin. Those tests check output against upstream artefacts vendored under `packages/permdock/tests/fixtures/standards` and pinned by `pnpm standards:fixtures` (the CloudEvents, A2A and Arazzo schemas, OCSF class definitions, and the examples in RFC 7520, 8037, 9421 and 7643). Where a standard publishes neither a schema nor examples, the test asserts the clauses the page cites. That is evidence that PermDock follows the text, not a certification.

The trade-off is that PermDock inherits the pace and gaps of each specification. Every unfinished text PermDock follows carries one of three postures: **build** against a pinned revision when the capability is needed now and a stable twin can carry the same information (OpenAPI 3.3 Security Profiles, Overlay 1.2, WebMCP, RAR remediation, the OpenTelemetry GenAI conventions, Web Bot Auth), **name** when only a public identifier must be reserved (GNAP as an OpenAPI scheme, the `permdock/jwt` checklist drafts), or **track**. The [watch list](/docs/standards/watch-list) shows the posture per row.

## Standards PermDock implements or targets [#standards-permdock-implements-or-targets]

| Standard | Version / date | Maturity | Where PermDock uses it |
| --- | --- | --- | --- |
| [Standard Schema](/docs/standards/standard-schema) | v1 (`@standard-schema/spec`), Standard JSON Schema | v1 | `resource()` definitions, [boundary validation](/docs/concepts/validation), catalog and OpenAPI schemas |
| [RFC 9457 Problem Details](/docs/standards/problem-details) | RFC 9457 | RFC | 403 bodies in [HTTP adapters](/docs/adapters/server-kernel), [errors](/docs/concepts/errors) |
| [OpenID AuthZEN Authorization API](/docs/standards/authzen) | 1.0, final Jan 2026 | final | Decision endpoint, [authzen adapter](/docs/adapters/authzen), [pdp provider](/docs/adapters/pdp) |
| [OAuth for agents](/docs/standards/oauth-agent-delegation) | RFC 9396, RFC 8693, RFC 9449, IETF drafts | RFCs plus IETF drafts | [Subject](/docs/concepts/subject) `actor` and `delegation`, `authorizationDetails` per permission, chain verification |
| [OpenID Connect](/docs/standards/openid-connect) | Core 1.0 (errata set 2, ISO/IEC 26131:2024), Discovery 1.0, Back-Channel Logout 1.0; RFC 8414, RFC 9068, RFC 9470 | final | `discovery` and `accept` in [`permdock/jwt`](/docs/adapters/jwt), `principal.issuer` and `assurance` claims; `logout_token` as a revocation input to [`permdock/ssf`](/docs/adapters/ssf) |
| [JOSE](/docs/standards/jose) | RFC 7515 to 7519 (JWS, JWE, JWK, JWA, JWT), RFC 8037, RFC 8725 and rfc8725bis, RFC 9864 | RFCs; bis in the RFC Editor queue | Token verification in [`permdock/jwt`](/docs/adapters/jwt); the `TokenVerifier` and `TokenSigner` interfaces; JWS-signed snapshots and approval tokens ([wire formats](/docs/concepts/wire-formats)) |
| [JWT authorization claims](/docs/standards/jwt-authorization-claims) | RFC 9068 section 2.2.3.1, RFC 7643 (SCIM) encoding; AuthZEN claims draft | RFCs plus an individual draft | Default `roles`, `groups`, `entitlements` mapping in [`permdock/jwt`](/docs/adapters/jwt) and provider mappers; `/search/resource` as a claim source |
| [SCIM 2.0](/docs/standards/scim) | RFC 7643, RFC 7644 (Sep 2015), RFC 9865 cursor pagination (2025); IPSIE AL1 profile draft for RFC 7523 bearers | RFCs; AL1 profile is a draft | [`permdock/scim`](/docs/adapters/scim) receiver writing a `DirectoryStore`, `directoryMembershipSource`; the PermDock Cloud hosted relay; `permdock rls` membership table mapping |
| [FAPI 2.0 Security Profile](/docs/standards/fapi-2) | FAPI 2.0 | final | [`permdock/jwt`](/docs/adapters/jwt) `profile: 'fapi2'`, `x-permdock-securityProfile` in [CLI openapi](/docs/cli/openapi) |
| [Agent docs standards](/docs/standards/agent-docs-standards) | AGENTS.md, Agent Skills, llms.txt (AAIF, Dec 2025) | community conventions | Shipped skills, `AGENTS.md`, `llms.txt`, [for AI agents](/docs/for-ai-agents) |
| [MCP authorization](/docs/standards/mcp-authorization) | Spec 2026-07-28, TS SDK v2 | released | [mcp adapter](/docs/adapters/mcp): `scopeChallenge`, MRTR `input_required`, RFC 8707, EMA |
| [OpenAPI 3.2 and 3.3](/docs/standards/openapi) | 3.2, Sep 2025 (3.1 via registered `x-oai-*` and `x-permdock-oauth2MetadataUrl`); 3.3 `v3.3-dev` with Security Profiles per Discussion #5304 | 3.2 released; 3.3 in development, built from a pinned draft | [openapi adapter](/docs/adapters/openapi), [CLI openapi](/docs/cli/openapi); `--target 3.3` emits the pinned Security Profile draft next to `x-permdock-securityProfile` |
| [OpenAPI Overlay](/docs/standards/openapi-overlay) | 1.1.0, Jan 2026; 1.2 in development | released; 1.2 draft, built behind `--overlay 1.2` | `permdock openapi` applies its security additions as an Overlay; `--overlay 1.2` emits the pinned reusable-actions draft |
| [Arazzo](/docs/standards/arazzo) | 1.1.0, May 2026 | released | `simulate({ arazzo, openapi })` and `permdock arazzo check` |
| [OpenAPI registries](/docs/standards/openapi-registry) | Extension and Namespace registries | living registries | Registering the `x-permdock-` namespace and the extensions PermDock emits |
| [WebMCP](/docs/standards/webmcp) | W3C WebML CG, Chrome docs | incubation | [webmcp adapter](/docs/adapters/webmcp) |
| [A2A](/docs/standards/a2a) | 1.0, Linux Foundation | 1.0 | [a2a adapter](/docs/adapters/a2a) |
| [Postgres RLS](/docs/standards/postgres-rls) | PostgreSQL `CREATE POLICY`, Supabase, Drizzle `pgPolicy`, Prisma 8 | shipped in PostgreSQL | [rls adapter](/docs/adapters/rls), [CLI rls](/docs/cli/rls) |
| [Shared Signals and CAEP](/docs/standards/shared-signals-caep) | SSF 1.0, CAEP 1.0, RISC 1.0; CAEP Interoperability Profile | final; interoperability profile is an implementer's draft | [ssf adapter](/docs/adapters/ssf) invalidating [snapshots](/docs/concepts/snapshots) |
| [RateLimit header fields](/docs/standards/ratelimit-headers) | `draft-ietf-httpapi-ratelimit-headers-11`, RFC 9110 `Retry-After` | IETF WG draft, built from the pinned draft | `429` and `RateLimit` fields for exhausted `limit` grants in HTTP adapters |
| [Web Bot Auth](/docs/standards/web-bot-auth) | `draft-meunier-webbotauth-httpsig-protocol-02`, RFC 9421 | IETF drafts, built from the pinned draft | `actor` in HTTP adapters (`webBotAuth` on `permdock/server`) |
| [Standards watch list](/docs/standards/watch-list) | Everything above plus the specifications PermDock only follows, including GNAP | mixed | Reviewed each release |

Related security frameworks that are not wire standards but shape the design: the [OWASP Top 10 for Agentic Applications](/docs/security/owasp-agentic) and the [threat model](/docs/security/threat-model).

## One decision, many vocabularies [#one-decision-many-vocabularies]

The standards above meet in one place: a `Decision` from `decide`. Each adapter translates the same three outcomes into the vocabulary its runtime already has.

| Outcome | HTTP (RFC 9457) | MCP | AI SDK 7 | AuthZEN |
| --- | --- | --- | --- | --- |
| `granted` | Handler runs | Handler runs | `'approved'` | `decision: true` |
| `denied` | 403 `.../denied` with `denials`, `alternatives` | `isError: true` with reasons and `alternatives` | `'denied'` | `decision: false`, `context.permdock.outcome: 'denied'` |
| `approval-required` | 403 `.../approval-required` with `token` | Elicitation carrying `token` | `'user-approval'` | `decision: false`, `context.permdock.outcome: 'approval-required'` |

No adapter ever emits an outcome outside these three; in particular the AI SDK adapter never returns `'not-applicable'`, the value that lets `@ai-sdk/policy-opa` fail open.

## How to read a standards page [#how-to-read-a-standards-page]

Every page in this section follows the same layout so an agent can scan it:

1. **What it is**: the specification, its status and the parts PermDock cares about.
2. **Why it matters for PermDock**: the problem it solves for a permissions library.
3. **How PermDock uses it**: the adapter, API or CLI command that implements it, in the exact shapes from the [quick start](/docs/getting-started/quick-start).
4. **Mapping table**: specification concept on the left, PermDock concept on the right.
5. **Sources**: the URLs the page was written from. Nothing on a standards page is asserted without one.

Questions the design leaves undecided live in the single Open questions list on the [roadmap](/docs/roadmap).

A page carries a `Status:` line under its frontmatter only when the code is `planned`, or when the specification is `tracking` (followed and designed against, with no adapter yet, like the [watch list](/docs/standards/watch-list)). A page for an unfinished text adds `Draft posture: build | name | track`; a `build` posture names the pinned revision in the same line, as [OpenAPI 3.2 and 3.3](/docs/standards/openapi) does.

## What PermDock deliberately does not standardise [#what-permdock-deliberately-does-not-standardise]

* **Policy language.** Roles are TypeScript data (`role`, `allow`, `deny`) and conditions are a small portable JSON AST, see [conditions](/docs/concepts/conditions). PermDock does not export Cedar or Rego and does not import them.
* **Token issuance.** PermDock consumes scopes, `authorization_details`, ID-JAG-derived tokens and delegation chains; it never mints them.
* **Authentication.** Providers (Supabase, Better Auth, Clerk, Convex) map an authenticated session to a subject. PermDock starts where authentication ends.

PermDock's own vocabularies are documented where other tools can reference them: the `x-permdock-*` extensions and JWS `typ` values on [OpenAPI registries](/docs/standards/openapi-registry), and the Problem Details `type` URIs on [Problem Details](/docs/standards/problem-details).
