Skip to main content

TokenExchangePolicy

warning

TokenExchangePolicy predates the OAuthServer configuration, and is documented for trust domains that already use it. Use OAuthServer for all new configurations. When a trust domain has both, OAuthServer takes precedence, and TokenExchangePolicy is ignored.

The TokenExchangePolicy Managed Configuration section lets workloads exchange users' ID tokens for on-behalf-of tokens. It lists the identity providers whose ID tokens are accepted, and optionally adds claims from those ID tokens to the on-behalf-of tokens it issues. Workloads request on-behalf-of tokens the same way under either configuration.

Example​

token-exchange-policy.yaml
section: TokenExchangePolicy
schema: v1
spec:
allowlist:
- issuer: https://idp.example.com
audiences:
- web-app
additionalClaims:
email: "{{jwt.claim.email}}"
department: "{{jwt.claim.department}}"

TokenExchangePolicy is a trust domain section. You can apply Managed Configuration through the Defakto API, Terraform, or the Defakto CLI. See applying configuration. For example, with the CLI:

defakto config set trust-domain --id <trust-domain-id> token-exchange-policy.yaml

Without a TokenExchangePolicy or an OAuthServer configuration that accepts users' tokens, every on-behalf-of token request is refused.

allowlist​

The identity providers whose ID tokens workloads may exchange. A presented ID token is accepted only when its issuer matches an entry's issuer, and one of its audiences is in the entry's audiences, both compared exactly. A token from an issuer that isn't listed is rejected before its keys are fetched.

FieldRequiredDescriptionExample
issuerYesThe identity provider's issuer URLhttps://idp.example.com
audiencesYesThe audiences that accepted ID tokens may carry, usually your application's client ID[web-app]

The token's JWT typ header must be JWT, or absent. A token whose typ names another kind of token, such as an access token (at+jwt), is rejected.

additionalClaims​

Claims to add to the on-behalf-of tokens the policy allows, copied from the user's ID token. Each key is the name of the claim to add, and each value is a single reference of the form {{jwt.claim.<name>}}, written with no spaces inside the braces.

  • Only string-valued claims can be referenced.
  • An added claim's name must match [a-zA-Z_][a-zA-Z0-9_]*. A referenced claim's name can contain letters, digits, underscores, and hyphens.
  • An added claim can't use a name that Defakto sets itself: iss, sub, aud, exp, nbf, iat, jti, obo, txn, auth_time, or nonce.
  • If the ID token doesn't have a referenced claim, the exchange is refused with invalid_request, rather than issuing a token without it.

When an on-behalf-of token is re-exchanged, its additional claims are carried forward with the values from the first exchange. Adding an entry to additionalClaims therefore makes on-behalf-of tokens issued before the change fail to re-exchange, because they don't carry the new claim. Expect chains in progress to restart after the change.

Re-exchange​

A workload that received an on-behalf-of token can exchange it for a new one whose audience is the next service, as described in Propagate a user's identity. Re-exchange is available whenever a TokenExchangePolicy is configured, and needs no allowlist entry, because the presented token is one your trust domain issued.