Best of 2021 – How to Revoke JSON Web Tokens (JWTs)

As we head into 2021, we at DevOps.com wanted to highlight the most popular articles of the year. Here is the seventeenth episode in our Best of 2021 series.

One of the most frequently asked questions about JSON Web Tokens (JWTs): Once released, how can they be revoked?

What are JWTs?

JSON Web Tokens are industry-standard mobile identity tokens. They are issued after a login is requested by a central identity server and are used to identify and authorize a user and grant access to resources. It can be served by clients such as browsers and external software. Applications and APIs can check to ensure that the caller is properly authenticated and authorized.

The challenges involved

One of the most common questions is how to revoke it. The problem is that once released, no further connection to the identity server is needed. This is one of the main benefits of decentralizing JWTs.

Let’s say you are using RSA public/private key signing to transfer data securely. After the IdP signs the JWT with the private key, any service with the public key can verify the integrity of the token.

Let’s use the Todo-Backend API as an example. Architecture might look like this:

Now, Todo-Backend can use JWT and the public key to verify a user’s ID and other attributes, and then use that ID to perform operations on that user’s data. Once the JWT is released, Todo-Backend does not communicate with the identity provider at all. As a result, if the administrator locks or deletes this user’s account in the identity provider, Todo-Backend will not know about it.

Manage cancellations using a distributed event system

The most common way to revoke access to JWT-protected resources involves setting their duration to a short period of time and revoking the refresh token so that the user cannot generate a new token. This does not cancel JWT In itself; It solves the root problem, which is access restriction.

In other words, you can set the JWT expiration time to a short period (eg, anywhere from a few seconds to ten minutes) and set the refresh token expiration to a longer period (eg a two-week or two-month window).

During normal flow, the Todo API accepts JWT until it expires, at which time access will be denied. At that time, the client can submit the update token to the identity provider, which will send a new JWT to the client. The new JWT will be valid for another ten minutes.

The administrator, at the identity provider, can revoke the refresh token at any time. Any subsequent request for a new JWT by a client with this refresh token will fail and access to the Todo API will be lost.

However, while ten minutes is not long, this time frame still carries risks.

One strategic way to approach this challenge is to set up a distributed event system that will notify services when refresh tokens are invalidated. When this event broadcast is received, the backgrounds/services will refresh the local cache that lists the users with the refresh codes that have been revoked. After checking the JWT, this cache will be checked to determine whether access should be revoked.

This distributed event method really eliminates the JWT, rather than just waiting for it to expire, as mentioned above.

Example of canceling JWTs

Below is a sample solution that provides support for events and webhooks that can be used to implement this revocation strategy. In this example, when the user logs out or their refresh token is otherwise invalidated, a jwt.refresh-token.revoke The event is issued. This includes the user ID and the application for which the cancellation occurred. Also includes the JWT lifetime for this app (600 seconds in the case below). Thus, any JWT for this user that was issued 600 seconds before the time this event was received is invalidated.

For example:

  • The user logs in, and a JWT “abc” is released at 1:11 PM. JWT is good until 1:21
  • The user logs out at 1:15. Added entry showing that any JWT for this app and user that expires before 1:25 are invalidated.
  • The application tries to use JWT “abc” at 1:16. Todo-Backend does not provide data because this JWT is a denylist based.
  • The user logs in, and a new “def” is issued in JWT at 1:18. JWT is good until 1:28.
  • The application tries to use JWT ‘def’ at 1:19. Todo-Backend provides the data because this JWT is good up to 1:28 and thus is not in the denylist.

JWT heroes

What you need to do is write a simple webhook to receive this event and report to JWTManager that the update token for form number For this user it has been revoked.

JWT web hook

JWTManager maintains a list of user IDs whose JWTs have been revoked. You can also use JWT identifiers (the “jti” prompt), which may be simpler in some cases. JWTManager also runs a cache-cleaning thread to remove expired users and avoid running out of memory.

Valid

For every API call, as well as all other validations that need to be done against JWT (checking for signature, expiration, source, etc.), the backend needs to be validated using JWTManager.

web hook configuration

As a final step, configure the webhook:

JWT web hook

The revocation process is simplified

Using the process described above, you can invalidate the user’s refresh token and broadcast the event using a web hook. Webhawk receivers then update the JWTManager, making the JWTs for that user unusable.

The good news is that you can use your webhook and event system to quickly build this feature into your app. You can also write JWTManager applications in Java, Node, and other client libraries for future use. Other languages, such as Ruby, have denilist implementations already written.

In the end, all that is required is the use of refresh tokens, an API that allows refresh tokens to be revoked, and a system for parsing the revocation event. This solution should work fine for most systems, even large systems with many backgrounds.

Leave a Comment