Use case

It’s a common case when REST API is secured with OAuth 2.0 and acts as a Resource server in terms of Auth 2.0. The easiest way to achieve this with Spring Security is to use Spring Boot OAuth2 Resource Server starter. This starter requires minimal configuration and works perfectly fine out of the box. You can see an example of the project in the official Spring repository with examples - Spring Security Examples.

Problem

The starter comes with some default JWT validators, e.g. JwtTimestampValidator to check if token is expired and JwtIssuerValidator to check that issuer URI matches the expected one (you can see the implementation in Spring Security repo). However, if you need to add some custom validator for JWT, there is no way to do this without redeclaring all the things that autoconfiguration does for you. As you can see in the starter’s source code, default validators are created inside the configuration instead of being injected to it (that would be a Spring way to do it).

Solution

Starting from Spring Boot 3.2.0 it’s not an issue anymore. Because now you can add custom JWT validators to Spring Security configuration simply by adding validator beans to your context. The beans should be of type OAuth2TokenValidator<Jwt>.

As an example let’s consider a case where we need to add a custom JWT claim validation. Spring Security provides a suitable JwtClaimValidator class that implements OAuth2TokenValidator interface. In that case, to add the validation we should declare a bean the following way:

  @Bean
  public JwtClaimValidator<String> customJwtClaimValidator() {
    return new JwtClaimValidator<>(
        "claimName",
        actualValue -> "expectedValue".equals(actualValue)
    );
  }

In this example we validate that claim claimName has value equal to expectedValue, otherwise the token is considered not valid.

Appreciations

Special thank you to Dmitry Denshchikov for the invaluable editing assistance, and to Spring Boot team for reviewing and accepting my PR for this feature.