Skip to content
Agent Identity

IETF · September 2023

OAuth 2.0 Demonstrating Proof of Possession (DPoP)

RFC 9449

D. Fett, B. Campbell, J. Bradley, T. Lodderstedt, M. Jones, D. Waite

RFCStableAuthenticationFoundationField guide

If the agent must use OAuth bearer tokens, DPoP is the most deployable way to make a stolen token from a prompt injection less useful. It is not a substitute for not putting tokens in the model context.

At a glance

Problem
Bearer access tokens are reusable if stolen. DPoP binds an access token to a key the client holds, using a signed proof JWT on each request, without requiring mTLS.
Identity / authn / authz
Sender-constrained authentication of the API call. The token still carries authorization.

Actors

  • Client
  • Authorization server
  • Resource server

In one board · Bearer vs DPoP

Photocopy, or pass glued to a key

Bearer

Photocopy

Authorization: BearerAuthorization: Bearer

Whoever holds the string may use it until it expires. Prompt injection, logs, and traces are copy machines.

  • Thief

    same pass, no key needed

    API

DPoP

Glued to a key

access token + cnf.jkt

Each request carries a short-lived proof JWT covering method and URL. Stolen paper without the private key is a blank.

  • Client with key

    pass + fresh proof

    API

RFC 9449. DPoP is application-layer proof — it works through TLS proxies. AAuth uses HTTP Message Signatures instead; do not stack proofs naively. mTLS is the other glue.

01

The gap for agents

Bearer access tokens are reusable if stolen from an agent prompt or log. DPoP (RFC 9449, September 2023) binds an access token to a client key using a signed proof JWT on each request, without requiring mTLS — the most deployable sender-constraint for agents that are not in a mesh.

It is not a substitute for keeping tokens out of model context. A stolen token plus a stolen key is still game over. It does stop 'I found a token in a gist' replay from a different machine.

02

Actors and trust boundaries

The client's DPoP key is the sender. The AS puts the JWK thumbprint in the access token cnf.jkt. The RS requires a fresh proof signed by that key covering htm and htu. TLS-terminating proxies do not break DPoP the way they break mTLS passthrough.

03

Mechanics

Client generates a DPoP key pair. Token endpoint (and later RS) receive a DPoP header: a JWT with typ dpop+jwt, jwk in the header, claims htm, htu, iat, jti, and when presenting an access token, ath (hash of the token). AS issues token_type=DPoP with cnf.jkt. RS checks proof freshness, uniqueness of jti (replay cache), and binding.

Nonce mechanism lets the RS/AS demand a fresh proof. Authorization codes can be bound to the DPoP key (FAPI 2.0 requires this when using DPoP).

DPoP proof JWT (htm, htu, iat, jti, ath)from spec
Quoted RFC 9449: per-request, short-lived, method and URI binding. ath when sending an access token.
cnf.jktfrom spec
Quoted: JWK thumbprint binding in the access token.
Authorization: DPoP / DPoP: <jwt>from spec
Quoted presentation: token_type DPoP, proof in the DPoP header — not Bearer.

04

Step-by-step flows

Flow 1

Bind then prove

  1. 1

    Client creates a DPoP key (often ephemeral per session).

  2. 2

    Token request includes a DPoP proof. AS returns an access token with cnf.jkt.

  3. 3

    Each RS call: new proof covering this method and URI, plus the access token, Authorization scheme DPoP.

  4. 4

    RS verifies token signature/introspection, jkt matches the proof key, proof signature, htm/htu, iat window, jti not replayed.

05

Identity vs authentication vs authorization

Sender-constrained authentication of the API call. The token still carries authorization. DPoP does not identify the user; OIDC still does that at the AS.

06

How it composes

07

What bites agent implementers

  • Proof replay

    Without a jti cache and tight iat, a captured proof+token pair replays at the same URI. Use nonce where possible.

  • htu mismatches

    Proxies that rewrite URLs break htu. Normalize carefully; do not skip the check.

  • Key in the agent filesystem

    If the DPoP private key sits next to the token in the same dump, you have not gained much. Isolate keys.

08

Stability — what you can ship

RFC 9449, September 2023. Stable. Ship it for any agent that must use OAuth tokens outside a mesh. https://www.rfc-editor.org/rfc/rfc9449.html

Catalog claims (short form)

DPoP proof JWT
Per-request, short-lived, includes htm/htu.
cnf.jkt
JWK thumbprint binding in the access token.

Implementer notes

DPoP is application-layer PoP and works through TLS-terminating proxies. AAuth instead uses HTTP Message Signatures (RFC 9421) as its PoP. Do not mix proofs naively.

Relationship to others

Primary sources

  • RFC 9449https://www.rfc-editor.org/rfc/rfc9449.html