Vault OAuth resource server
Vault acts as an OAuth resource server with distinct OAuth server profiles for trusted IdP or authorization servers.
A server profile defines how Vault validates JWTs from a specific authorization server. Each profile represents a trust relationship with one issuer. You can configure multiple profiles to accept tokens from different authorization servers.
When Vault receives an OAuth JWT, it extracts the iss issuer claim and looks
up the corresponding profile. If no profile matches the issuer, Vault rejects
the token.
How OAuth JWTs and agent registry work together
When a client presents an OAuth JWT in the X-Vault-Token header, Vault uses
the configured profiles to validate the token. Vault extracts the iss claim,
finds the matching enabled profile, verifies the token signature against the
profile's keys, and checks the token's claims, including audience, expiration,
and required fields, against the profile's settings.
After validation, Vault resolves the caller's identity through a Vault Identity
entity alias bound to the profile's issuer and
the value of the configured user_claim. The entity's policies become the
caller's baseline permissions.
Vault then checks the Agent Registry requirement for the request:
- In a delegated, on-behalf-of request, the actor must have a registration.
- In a direct, non-delegated request, the subject must have a registration.
If the required entity has no Agent Registry record, Vault rejects the OAuth credential.
Profile fields
| Field | Description |
|---|---|
name | Unique name for the profile within the namespace. Used as the path identifier in API operations. |
config_id | Stable unique identifier generated by Vault when the profile is created. |
mount_accessor | Synthetic mount accessor Vault derives from the namespace ID and config_id, in the format oauth-resource-server_<namespace_id>_<config_id>. Vault returns the accessor on create, read, and list responses, and uses it to identify aliases backed by the profile. Read-only. |
issuer_id | The expected iss claim value. Must be unique within its locality (local or global) in the namespace. Required on create. |
local | Requires Vault 2.2.0 or later. If true, Vault stores the profile in cluster-local storage and never replicates it to other clusters. Defaults to false. Immutable after creation. Profile names must be unique across both local and global profiles in the namespace. You cannot create a local and a global profile with the same name. |
use_jwks | If true, Vault fetches public keys from a JWKS endpoint. If false, Vault uses static PEM-encoded public keys. Defaults to true. |
jwks_uri | The JWKS endpoint URI to fetch signing keys from. Required when use_jwks is true. |
jwks_ca_pem | Optional CA certificate, PEM-encoded, for TLS verification of the JWKS endpoint. |
public_keys | List of static public keys, each with a key_id and pem field. Required when use_jwks is false. |
audiences | List of allowed aud claim values. |
user_claim | The JWT claim that identifies the user. Defaults to sub. |
authorization_details_claim | Requires Vault 2.2.0 or later. The JWT claim that contains the authorization details for Rich Authorization Requests. Defaults to authorization_details. |
unique_id_claim | The JWT claim that uniquely identifies a specific token. Defaults to jti. |
actor_claim | The JWT claim that Vault uses to resolve an actor's entity. Defaults to act.sub. |
supported_algorithms | List of accepted signing algorithms, for example, RS256, ES256, or EdDSA. Refer to Supported algorithms for the full list. |
jwt_type | The expected token type: access_token. Defaults to access_token, the only type currently supported. |
clock_skew_leeway | Tolerance in seconds for clock differences when validating time-based claims. |
no_default_policy | If true, tokens authenticated through the profile do not automatically receive the default policy. |
optional_authorization_details | If true, makes the authorization_details claim optional for tokens validated by the configured profile. |
enabled | If false, the profile is ignored during JWT validation. Defaults to true. |
Key validation modes
Each profile uses exactly one of two mutually exclusive modes for validating JWT signatures:
JWKS mode (
use_jwks=true): Vault fetches the authorization server's public keys from the configuredjwks_uri. Vault caches these keys and refreshes them when it encounters an unrecognized key ID, subject to rate limiting to prevent abuse.Static key mode (
use_jwks=false): Vault uses PEM-encoded public keys provided directly in the profile configuration. Each key includes akey_idthat Vault matches against the JWTkidheader.
You cannot configure both jwks_uri and public_keys on the same profile.
Supported algorithms
Profiles accept asymmetrically signed JWTs only. The following signing algorithms are supported:
- RSA: RS256, RS384, RS512, PS256, PS384, PS512
- ECDSA: ES256, ES384, ES512
- Ed25519: EdDSA
The EdDSA algorithm applies to Ed25519 keys only. Profiles accept Ed25519 keys
as PEM-encoded static keys or as OKP keys served from a JWKS endpoint.
HMAC algorithms, including HS256, HS384, and HS512, opaque tokens, and JWE, or JSON Web Encryption, are not supported.
Local profiles
By default, profiles are global. Vault stores profiles in replicated storage and propagates them to all performance secondary clusters automatically.
Set local=true when you want to create a profile and make it local to the cluster
where you create it. Local profiles:
- Are stored in cluster-local storage and never enter the replication WAL.
- Exist only on the cluster where they were created. Vault does not make local profiles visible on other clusters.
- Can be created, updated, and deleted directly on a performance secondary without write-forwarding to the primary.
Profile names are unique across both localities in a namespace. You cannot create a local profile and a global profile with the same name. To create a profile with a different locality than an existing profile of the same name, delete the existing profile first.
The local field is immutable. To change the locality of a profile, delete it and
recreate it with the desired local value.
When to use local profiles
Use local profiles when you need to configure trust for an issuer that is specific to one cluster and should not propagate elsewhere. For example, when you have a private authorization server that operates only in a single region.
Replication-time collision
A replication-time collision occurs when Vault replicates a global profile from the primary to a secondary that already has a local profile with the same name. Because the primary cannot know about local profiles on a secondary, the primary operator cannot prevent the collision in advance.
When a collision occurs, Vault on the secondary logs a warning and continues to serve the local profile. Vault does not index the replicated global profile on the secondary. The global profile has no effect on the secondary. The global profile continues to exist on the primary and on other secondaries that do not have a conflicting local profile.
After you delete the local profile from the secondary, Vault re-indexes the global profile on the secondary. Subsequent JWT validation on the secondary uses the global profile.
Issuer uniqueness
Each issuer_id must be unique per locality in the namespace:
- Two local profiles in the same namespace cannot share an
issuer_id. - Two global profiles in the same namespace cannot share an
issuer_id. - A local profile and a global profile may share an
issuer_id. You can use shared issuer IDs when both profiles cover the same authorization server but serve different clusters.
Enabling and disabling profiles
Set enabled to false to disable a profile without deleting it. Disabled
profiles are skipped during JWT validation. This allows you to temporarily
suspend trust for a specific issuer without losing the profile configuration.
Namespace isolation
Profiles are scoped to the namespace in which they are created:
- Profiles in the root namespace are accessible only within the root namespace.
- Profiles in a child namespace are accessible only within that child namespace.
- There is no cross-namespace visibility or inheritance of profiles.
Each namespace maintains its own independent set of profiles with its own issuer uniqueness constraint.
Entity aliases for profiles
Vault resolves the caller's identity through an
entity alias bound to the
profile, so every principal that authenticates through a profile needs an alias.
Profiles have no auth mount, so Vault identifies profile-backed aliases with the
synthetic mount_accessor described in Profile fields.
You have three ways to tell Vault which profile backs an alias:
| Method | Fields | Behavior |
|---|---|---|
| Profile reference | profile_name or config_id, with external_id | Vault resolves the profile and derives the mount accessor and the issuer from it. Requires Vault 2.2.0 or later. |
| Issuer shortcut | issuer, with external_id | Vault resolves the profile whose issuer_id matches issuer and derives the mount accessor from it. |
| Explicit accessor | mount_accessor | Vault uses the accessor you supply. Read the accessor from the profile rather than assembling it. |
We recommend a profile reference. You pass the same profile_name or
config_id value that the profile endpoints return, and Vault derives
everything else, so an alias cannot end up carrying an accessor and an issuer
that point at different profiles.
Profile references follow the same boundaries as the profiles themselves:
- Vault resolves the reference in the request namespace. A profile in another namespace does not resolve.
- An alias for a profile created with
local=trueis a local alias. profile_name,config_id, andmount_accessorare mutually exclusive.- You can reference a profile only when you create an alias. An alias keeps the mount accessor it was created with.
Refer to Reference an OAuth resource server profile for the full rules.