Validating an Access Token
OAuth 2 Resource Servers restrict access to APIs by requiring a valid OAuth 2 access token to be present in the
Authorization header as a bearer token (example: Authorization: Bearer ACCESS_TOKEN). It is the Resource Server’s
responsibility to properly validate the access token.
In addition to validating the access token as a JWT, a Resource Server must validate sender-constrained access tokens against a required DPoP proof.
Validate the Access Token JWT
The access token will be provided in the Authorization header preceded by the string Bearer.
The authorization scheme is case-insensitive. Resource servers must accept all the following forms:
Authorization: Bearer ACCESS_TOKENAuthorization: bearer ACCESS_TOKENAuthorization: BEARER ACCESS_TOKEN
A JWT library should be used to validate the token. When validating time based claims such as exp and iat,
most JWT libraries allow configuration of a clock drift. A clock drift of 60 seconds or less should be used.
- Validate the ACCESS_TOKEN as a signed JWT. The ACCESS_TOKEN signature should be validated against the public key
published in the JWKS_URL by the Jack Henry Authorization Server. Multiple keys may be present in the JWKS_URL.
The
kidheader in the ACCESS_TOKEN JWT will specify which key is to be used for validation. - Ensure that the
expclaim is in the future. - Ensure that the
iatclaim is now or in the past. - Ensure that the access token does not have a
cnfclaim or perform all the validation for a sender constrained access token and require a validDPoPheader.
Validate a Sender Constrained Access Token
The access token will be provided in the Authorization header preceded by the string DPoP
(example: Authorization: DPoP ACCESS_TOKEN). The access token
is required to be sender constrained meaning proof of ownership must also be provided.
See Demonstrating Proof of Possession (DPoP) for more details.
The authorization scheme is case-insensitive. Resource servers must accept all the following forms:
Authorization: DPoP ACCESS_TOKENAuthorization: DPOP ACCESS_TOKENAuthorization: dpop ACCESS_TOKEN
When provided with a DPoP scheme, the access token must contain a cnf claim.
If a cnf claim is missing, the token is not sender-constrained. The Resource Server must ensure a valid
DPoP proof is present. See https://datatracker.ietf.org/doc/html/rfc9449#name-checking-dpop-proofs
The following checks must all be performed when the DPoP scheme is used or the Access Token contains a
cnf claim. The checks may be performed in any order.
- Ensure only one DPoP header is present on the request.
- The DPoP HTTP request header field value is a single and well-formed JWT.
- The DPoP JWT includes all the required claims:
jtihtmhtuiatath
- The
typheader of the DPoP JWT is the value “dpop+jwt”. - The
algheader of the DPoP JWT is one of the supported algorithms and is not none. Resource Servers must support all the DPoP algorithms. - The DPoP JWT signature verifies with the public key contained in the
jwkheader of the DPoP JWT. - The
jwkheader of the DPoP JWT does not contain a private key. - The
htmclaim matches the HTTP method of the current request. - The
htuclaim matches the HTTP URI value for the HTTP request in which the JWT was received, ignoring any query and fragment parts. - The creation time of the JWT, as determined by the
iatclaim is within an acceptable window. 60 seconds is the recommended lifetime a Resource Server should support (in addition to clock drift). - The value of the
athclaim equals the result of a base64url encoding the SHA-256 hash of ASCII encoding the Access Token’s raw value. - The JWT thumbprint of the
jwkheader of the DPoP JWT matches thejktkey of thecnfclaim in the Access Token. See https://datatracker.ietf.org/doc/html/rfc7638.
In addition, Resources Servers should do the following:
- Use syntax-based normalization before comparing the
htuclaim. - Use scheme-based normalization before comparing the
htuclaim. - Ensure that the
jtivalue has not been seen within a reasonable time window. Example: if theiatclaim is allowed to be 60 seconds old and a clock-drift of 60 seconds is used, ajtivalue should be unique within a 2 minute window.
Additional Validation
A valid Access Token will contain the following claims which a Resource Server may use to further validate the call.
client_id- The OAuth client id of the calling applicationinstitutionId- The universal institution id in which the OAuth client id is configured.sub- The associated user id of the caller. This is either the human who consented for the authorization code flow or the service account associated with the client credentials flow. Thesubclaim can be used to validate the permissions of the caller.
- Have a how-to question? Seeing a weird error? Get help on StackOverflow.
- Register for the Developer Office Hours where we answer technical Q&A from the audience.