Verifying a JSON web token
These steps describe verifying a user pool JSON Web Token (JWT).
Topics
Prerequisites
Your library, SDK, or software framework might already handle the tasks in this section. For example, Amazon Cognito SDKs provide user pool token handling and management on the client side. Likewise, the Mobile SDK for iOS and the Mobile SDK for Android automatically refresh your ID and access tokens if two conditions are met: A valid (unexpired) refresh token must present, and the ID and access tokens must have a minimum remaining validity time of 5 minutes. For information on the SDKs, and sample code for JavaScript, Android, and iOS, see Amazon Cognito user pool SDKs.
Many libraries are available for decoding and verifying a JSON Web Token (JWT). If you
must manually process tokens for server-side API processing or if you are using other
programming languages, these libraries can help. See the OpenID foundation list of libraries for working
with JWT tokens
Step 1: Confirm the structure of the JWT
A JSON Web Token (JWT) includes three sections:
-
Header
-
Payload
-
Signature
11111111111.22222222222.33333333333 |
These sections are encoded as base64url strings and are separated by dot (.) characters. If your JWT does not conform to this structure, consider it not valid and do not accept it.
Step 2: Validate the JWT signature
The JWT signature is a hashed combination of the header and the payload. Amazon Cognito generates two pairs of RSA cryptographic keys for each user pool. One of the private keys is used to sign the token.
To verify the signature of a JWT token
-
Decode the ID token.
You can use AWS Lambda to decode user pool JWTs. For more information, see Decode and verify Amazon Cognito JWT tokens using AWS Lambda
. The OpenID Foundation also maintains a list of libraries for working with JWT tokens
. -
Compare the local key ID (
kid
) to the public kid.-
Download and store the corresponding public JSON Web Key (JWK) for your user pool. It is available as part of a JSON Web Key Set (JWKS). You can locate it by constructing the following URL for your environment:
https://cognito-idp.{region}.amazonaws.com/{userPoolId}/.well-known/jwks.json
For more information on JWK and JWK sets, see JSON web key (JWK)
. Note Downloading and storing the JWK for your user pool is a one-time step before your web API operations can process tokens. After doing so, you can perform the following steps each time the ID token or the access token is used with your web API operations.
This is a sample
jwks.json
file:{ "keys": [{ "kid": "1234example=", "alg": "RS256", "kty": "RSA", "e": "AQAB", "n": "1234567890", "use": "sig" }, { "kid": "5678example=", "alg": "RS256", "kty": "RSA", "e": "AQAB", "n": "987654321", "use": "sig" }] }
- Key ID (
kid
) -
The
kid
is a hint that indicates which key was used to secure the JSON web signature (JWS) of the token. - Algorithm (
alg
) -
The
alg
header parameter represents the cryptographic algorithm that is used to secure the ID token. User pools use an RS256 cryptographic algorithm, which is an RSA signature with SHA-256. For more information on RSA, see RSA cryptography. - Key type (
kty
) -
The
kty
parameter identifies the cryptographic algorithm family that is used with the key, such as "RSA" in this example. - RSA exponent (
e
) -
The
e
parameter contains the exponent value for the RSA public key. It is represented as a Base64urlUInt-encoded value. - RSA modulus (
n
) -
The
n
parameter contains the modulus value for the RSA public key. It is represented as a Base64urlUInt-encoded value. - Use (
use
) -
The
use
parameter describes the intended use of the public key. For this example, theuse
valuesig
represents signature.
- Key ID (
-
Search the public JSON web key for a
kid
that matches thekid
of your JWT.
-
-
Use a JWT library, such as the aws-jwt-verify library on GitHub
, to compare the signature of the issuer to the signature in the token. The issuer signature is derived from the public key (the RSA modulus "n"
) of thekid
in jwks.json that matches the tokenkid
. You might need to convert the JWK to PEM format first. The following example takes the JWT and JWK and uses the Node.js library, jsonwebtoken, to verify the JWT signature:
Step 3: Verify the claims
To verify JWT claims
-
Verify that the token is not expired.
-
The
aud
claim in an ID token and theclient_id
claim in an access token should match the app client ID that was created in the Amazon Cognito user pool. -
The issuer (
iss
) claim should match your user pool. For example, a user pool created in theus-east-1
Region will have the followingiss
value:https://cognito-idp.us-east-1.amazonaws.com/
.<userpoolID>
-
Check the
token_use
claim.-
If you are only accepting the access token in your web API operations, its value must be
access
. -
If you are only using the ID token, its value must be
id
. -
If you are using both ID and access tokens, the
token_use
claim must be eitherid
oraccess
.
-
You can now trust the claims inside the token.