WIMSE Workload Credentials
A workload identity that can pass through proxies without becoming a bearer token.
Flows / No human
A workload identity that is bound to a key and proven on every request, so it survives the gateways and proxies that agent traffic passes through.
Mutual TLS gives two workloads strong mutual authentication, until something in the middle terminates the connection. Agent traffic passes through a lot of middle: API gateways, MCP gateways, service-mesh waypoints, inspection proxies. Each one ends the TLS session, and the caller’s certificate goes no further. The usual fallback is a bearer JWT in a header, which anyone along the path can copy and replay.
The IETF WIMSE working group is standardizing a credential built for this. A Workload Identity Token (WIT) is a JWT that names the workload and carries its public key. It is never accepted on its own. Each request must also carry proof that the sender holds the matching private key: either a Workload Proof Token (WPT), a small signed JWT bound to this request, or an HTTP Message Signature over the request itself. A proxy can forward both, and a thief who copies them gets nothing reusable.
The working group’s agent architecture document says plainly that agents are workloads, and builds on exactly this.
8 steps between 4 parties. Each step shows the message and who holds which credential afterward. Use ←→ or select any arrow.
Drag to see every party and step. Tap a step to jump to its explanation.
The private key stays in the workload. Only the public key is sent to the issuer.
Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
How the issuer recognizes the workload is the platform’s business: process attestation through the SPIFFE Workload API, a Kubernetes service account token, a cloud instance identity. The draft does not prescribe it.
Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
A signed JWT of type wit+jwt. The subject is the workload’s identifier, a URI scoped to a trust domain. The cnf claim holds the workload’s public key. There is no audience: the same WIT is shown to every peer, which is safe because it is worthless without the key.
// header: { "alg": "ES256", "kid": "issuer-key-1", "typ": "wit+jwt" }
{
"iss": "https://issuer.example.org",
"sub": "spiffe://example.org/ns/agents/sa/research-agent",
"exp": 1745512510,
"jti": "x-_1CTL2cca3CSE4cwb_l",
"cnf": {
"jwk": { "kty": "OKP", "crv": "Ed25519", "x": "1CXXvflN_LVVsIsYXsUvB03JmlGWeCHqQVuouCF92bg" }
}
}Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
A very short-lived JWT of type wpt+jwt, signed with the private key. aud is the URL being called, wth is a hash of the WIT, and jti makes it single-use. Optional claims bind it to an access token or a transaction token traveling in the same request.
// header: { "alg": "EdDSA", "typ": "wpt+jwt" }
{
"aud": "https://tools.example.org/search",
"exp": 1745510016,
"jti": "__bwc4ESC3acc2LTC1-_x",
"wth": "MeOILk2AJHh6czknhZ2c7TkiVpeFTC_cyYAonmT7mkI"
}Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
Each has its own header field. Neither goes in Authorization, which stays free for a user’s access token.
POST /search HTTP/1.1
Host: tools.example.org
Workload-Identity-Token: eyJhbGciOiJFUzI1NiIsInR5cCI6IndpdCtqd3QifQ…
Workload-Proof-Token: eyJhbGciOiJFZERTQSIsInR5cCI6IndwdCtqd3QifQ…
Authorization: Bearer <user's delegated access token>Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
The TLS session from the agent ended at the gateway. A client certificate would be gone at this point. The headers pass through untouched, and the gateway itself can verify them to apply policy.
Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
It verifies the WIT against the issuer’s keys, then verifies the WPT’s signature with the public key inside the WIT, checks that wth matches, that aud is this endpoint, and that the proof is fresh and unseen. Only then does it treat the caller as research-agent.
Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
Anything that copied the headers on the way, including the gateway’s logs, has a proof valid for one request to one URL for a few seconds.
Who holds what after this step
Parties not listed hold none of this flow’s credentials at this point.
Authorization header or accepted as a bearer token. A receiver that skips the proof has reintroduced the problem.The working group split its original protocol draft into separate documents. One defines the credentials. Three define how to prove possession: the Workload Proof Token shown here, HTTP Message Signatures (which can also sign the response), and mutual TLS with an X.509 workload certificate for cases where nothing sits in the path. The first two are for the application layer and survive proxies.
SPIFFE has added the WIT-SVID as a third identity document type, at incubating stability, and SPIRE has experimental support behind a flag. Treat this as something to prototype with, not to depend on.
See the full tracker for status and links.
A workload identity that can pass through proxies without becoming a bearer token.
The workload equivalent of a DPoP proof.
End-to-end caller authentication through TLS-terminating gateways.
Includes a section on agents: each hop in an agent chain must explicitly scope and re-bind the security context.
The closest thing to an IETF reference architecture for agent authentication and authorization. Its opening position: agents are workloads.
The de facto workload identifier reused by the IETF agent architecture draft, cloud agent-identity products and agent gateways.
The building block under Web Bot Auth, the WIMSE HTTP signature profile, AAuth, and the card networks’ agent protocols.
Every agent process gets a cryptographic identity from the infrastructure it runs on, and uses it to authenticate both ends of every connection.
Bind a token to a key so that stealing the token is not enough to use it.
Inside your own infrastructure, replace the access token with a short-lived token that pins down one transaction and travels the whole call chain.
Your agent uses an identity established by its runtime to obtain short-lived access from a system that trusts that identity.