Skip to content

PATTERN Cited by 1 source

Layered JWT + mesh auth

Pattern

Layered JWT + mesh auth is the two-layer authorization shape for agent traffic inside an enterprise mesh: an end-user JWT authenticates + coarsely authorizes the human on whose behalf an agent is acting, and a SPIFFE-style mesh identity authenticates the calling workload. Both travel on every request; both are enforced; they compose.

Canonical wiki statement (Pinterest, 2026-03-19):

"At runtime, almost every MCP call is governed by two layers of auth: end-user JWTs and mesh identities." (Source: sources/2026-03-19-pinterest-building-an-mcp-ecosystem-at-pinterest)

Two layers, two jobs

Layer 1 — end-user JWT (who is the human?)

  • Client (AI chat web, IDE plugin, chat-platform AI bot) performs OAuth against the enterprise's internal auth stack.
  • OAuth issues a JWT with the user's identity + business-group membership + optional roles.
  • The client carries the JWT on every MCP call.
  • Envoy at the mesh ingress validates the JWT and maps it to headersX-Forwarded-User, X-Forwarded-Groups, and related.
  • Envoy enforces coarse-grained policies at the server-reachability altitude ("AI chat webapp in prod may talk to the Presto MCP server, but not to experimental MCP servers in dev namespaces").

Layer 2 — mesh identity (who is the calling workload?)

  • Each workload has a SPIFFE-style mesh identity issued by the service mesh (e.g. SPIRE + Envoy SDS, or a company-specific mesh-identity substrate).
  • The mesh validates workload-to-workload traffic independently of end-user JWT.
  • For low-risk read-only scenarios with no end user in the loop, mesh identity alone is sufficient: the server authorizes based on the calling service's mesh identity.

Optional sub-layer — in-process per-tool decorator

"Inside the server, tools use a lightweight @authorize_tool(policy='…') decorator to enforce finer-grained rules (for example, only Ads-eng groups can call a get_revenue_metrics, even if the server itself is reachable from other orgs)."

The decorator reads the headers Envoy wrote (X-Forwarded-User / X-Forwarded-Groups) and enforces per-tool policy. See patterns/per-tool-authorization-decorator.

Why layered — single-layer designs fail

  • JWT alone — covers the human but not workload-to-workload calls (the MCP server calling another internal service). Also no defense-in-depth: JWT compromise is catastrophic.
  • Mesh identity alone — no human attribution; can't enforce "this user's role requires data access" (the business-group gating axis).
  • OAuth-per-server (the MCP spec's shape) — per-server consent dialogs + per-server tokens. High user friction. Pinterest explicitly rejects this for internal agents: "users already authenticate against our internal auth stack when they open a surface like the AI chat interface, so we piggyback on that existing session."

Enforcement altitudes

Altitude What's enforced Where
Transport JWT valid + signed Envoy
Mesh Calling workload identity Service mesh (SPIFFE / SPIRE)
Server-reachability Can user reach this server Envoy policy using header-mapped JWT claims
Session Can user open a session (business-group gate) In-server or registry pre-flight
Tool-call Can user call this specific tool @authorize_tool(policy='…') decorator

Each altitude is a checkpoint; each can fail-closed independently; compromise of any single layer does not bypass the others.

The contrast with per-server OAuth

The MCP authorization spec defines an OAuth 2.0 flow where users authenticate with each MCP server separately — consent screens, per-server token management, per-server authorization code exchanges. Pinterest's posture: "There is no additional login prompt or consent dialog when a user invokes an MCP tool. Envoy and our policy decorators handle authorization transparently in the background, giving us fine-grained control over who can call which tools without surfacing the complexity of per-server authorization flows to the end user."

Trade-offs:

  • Per-server OAuth — higher user transparency (every server explicitly consented to), higher friction (N consent dialogs), less intra-org uniformity.
  • Layered JWT + mesh — piggyback on existing SSO (zero incremental friction), enterprise-wide policy consistency, assumes trust in the enterprise auth stack.

The layered pattern is a deliberate enterprise integration choice, not a rejection of the spec — the spec is for cross-org / public MCP; layered JWT + mesh is for inside-the-org MCP.

Seen in

Last updated · 319 distilled / 1,201 read