Skillmine Auth - Documentation
  • Introduction
  • Get started
    • Create and integrate the first application
    • Customize sign-in experience
    • Enable social sign-in
    • Configuring the SSO (Single Sign On):
  • Protect your API
    • Protect your API on Node(Express)
    • Protect your API on Python
    • Protect your API on Spring Boot
  • Manage users
    • Manage users using Admin Console
    • Manage users using Management API
  • Auth Architecture
  • SSO Dashboard
  • SSO Application
  • Blueprints
  • Groups & Permissions
    • User Roles
    • Permissions
    • Group Category
    • Group
  • Workflow
    • Workflow
    • Manage Request
  • Settings
    • Authentication Methods
    • Schemas
    • Consent Management
    • Password Policy
    • CAPTCHA's
    • Site Group
    • Messaging Template
      • Built-In Template
      • Custom Template
    • Webhook Settings
    • Connectors
    • Device Restriction
    • MFA
      • End User Configuration Guide
      • End User Usage
    • MFA Settings
    • Payment Gateway
      • Providers
      • Payment Flows
      • Payment History
    • Open Id Connect Setttings
      • Client Settings
      • Scopes
    • SCIM
  • You don't need a user table
  • Localization
  • API Resource
  • Users
    • Search Users
    • Invite User
    • Create User
    • Bulk User Operations
      • Creation
      • Updation
      • Deletion
      • Reset Password
  • Report
    • User Report
    • Captcha Failure Report
    • Inactive users report
    • Provider wise Report
    • Webhook Report
    • Notification Report
    • Audit Trail Report
    • Mac Restriction Report
    • RADIUS Audit Trail Report
  • Social identities
  • References
    • OpenID Connect
  • Usecases
    • ECommerce Site Integration
    • Groups & Roles Integration
    • Custom Provider Integration
    • Salesforce Integration
  • Connectors
    • Office365
Powered by GitBook
On this page
  • Start a Spring Boot project​
  • Add dependencies​
  • Get issuer and JWKS URI​
  • Configure application​
  • Provide audience validator​
  • Configure Spring Security​
  • Add APIs​
  1. Protect your API

Protect your API on Spring Boot

PreviousProtect your API on PythonNextManage users

Last updated 2 years ago

Your web application may run on the server-side using Spring Boot framework. For now, you need to integrate Auth in Spring Boot manually. This article guides you on how to finish it step by step. And we use Gradle, Java, and Spring Security to take the example.

Start a Spring Boot project

With , you can quickly start a Spring Boot project. Use the following options:

  1. Gradle Project

  2. Language: Java

  3. Spring Boot: 2.7.2

Generate and open the project.

Add dependencies

Add the dependencies to your Gradle project build file build.gradle:

dependencies {
   implementation 'org.springframework.boot:spring-boot-starter-web'
   implementation 'org.springframework.boot:spring-boot-starter-oauth2-resource-server'
}

NOTE

Since Spring Boot and Spring Security have built-in support for both OAuth2 resource server and JWT validation, you DO NOT need to add additional libraries from Auth to integrate.

See and for more details.

Before moving on, you will need to get an issuer and a JWKS URI to verify the issuer and the signature of the Bearer Token (access_token).

All the latest Auth Authorization Server Configurations can be found by https:///.well-known/openid-configuration, including the issuer, jwks_uri and other authorization configs. For example:

{
 // ...
 "issuer": "https://<your-auth-domain>",
 "jwks_uri": "https://nightly-accounts-api.complyment.com/.well-known/jwks.json"
 // ...
}

Use an application.yml file (instead of the default application.properties) to configure the server port, audience, and OAuth2 resource server.

# path/to/project/src/main/resources/application.yaml
server:
 port: 3000

auth:
 audience: http://localhost:3000/

spring:
 security:
   oauth2:
     resourceserver:
       jwt:
         issuer-uri: <your-auth-issuer-uri> # e.g. https://nightly-accounts-api.complyment.com
         jwk-set-uri: <your-auth-jwks-uri> # e.g. https://nightly-accounts-api.complyment.com/.well-known/jwks.json
  • audience: The unique API identifier (i.e. API indicator) of your protected API resource.

  • spring.security.oauth2.resourceserver.jwt.issuer-uri: The iss claim value and the issuer URI in the JWT issued by Auth. Fill out the issuer value from the previous section.

  • spring.security.oauth2.resourceserver.jwt.jwk-set-uri: Spring Security uses this URI to get the authorization server's public keys to validate JWT signatures. Fill out the jwks_uri value from the previous section.

Provide your own AudienceValidator class that implements the OAuth2TokenValidator interface to validate whether the required audience is present in the JWT.

// path/to/project/src/main/java/io/auth/springboot/sample/validator/AudienceValidator.java
package io.auth.springboot.sample.validator;
import org.springframework.security.oauth2.core.OAuth2Error;
import org.springframework.security.oauth2.core.OAuth2TokenValidator;
import org.springframework.security.oauth2.core.OAuth2TokenValidatorResult;
import org.springframework.security.oauth2.jwt.Jwt;

public class AudienceValidator implements OAuth2TokenValidator<Jwt> {
    private final OAuth2Error oAuth2Error = new OAuth2Error("invalid_token", "Required audience not found", null);
    private final String audience;
    public AudienceValidator(String audience) {
        this.audience = audience;
    }
    @Override
    public OAuth2TokenValidatorResult validate(Jwt jwt) {
        if (!jwt.getAudience().contains(audience)) {
            return OAuth2TokenValidatorResult.failure(oAuth2Error);
        }
        return OAuth2TokenValidatorResult.success();
    }
}

Spring Security makes it easy to configure your application as a Resource Server and validate the JWT from the Bearer Token in the request header.

You need to provide instances of JwtDecoder and SecurityFilterChain (as Spring beans), and add the @EnableWebSecurity annotation.

// path/to/project/src/main/java/io/auth/springboot/sample/configuration/SecurityConfiguration.java
package io.auth.springboot.sample.configuration;

import com.nimbusds.jose.JOSEObjectType;
import com.nimbusds.jose.proc.DefaultJOSEObjectTypeVerifier;
import com.nimbusds.jose.proc.SecurityContext;
import io.auth.springboot.sample.validator.AudienceValidator;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configurers.oauth2.server.resource.OAuth2ResourceServerConfigurer;
import org.springframework.security.oauth2.core.DelegatingOAuth2TokenValidator;
import org.springframework.security.oauth2.core.OAuth2TokenValidator;
import org.springframework.security.oauth2.jwt.Jwt;
import org.springframework.security.oauth2.jwt.JwtDecoder;
import org.springframework.security.oauth2.jwt.JwtValidators;
import org.springframework.security.oauth2.jwt.NimbusJwtDecoder;
import org.springframework.security.web.SecurityFilterChain;

@EnableWebSecurity
public class SecurityConfiguration {

    @Value("${auth.audience}")
    private String audience;
    @Value("${spring.security.oauth2.resourceserver.jwt.issuer-uri}")
    private String issuer;
    @Value("${spring.security.oauth2.resourceserver.jwt.jwk-set-uri}")
    private String jwksUri;
    @Bean
    public JwtDecoder jwtDecoder() {
        NimbusJwtDecoder jwtDecoder = NimbusJwtDecoder.withJwkSetUri(jwksUri)
                // The decoder should support the token type: Access Token + JWT.
                .jwtProcessorCustomizer(customizer -> customizer.setJWSTypeVerifier(
                        new DefaultJOSEObjectTypeVerifier<SecurityContext>(new JOSEObjectType("at+jwt"))))
                .build();
        jwtDecoder.setJwtValidator(new DelegatingOAuth2TokenValidator<>(
                new AudienceValidator(audience),
                new JwtIssuerValidator(issuer),
                new JwtTimestampValidator()));
        return jwtDecoder;
    }
    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        http.oauth2ResourceServer(OAuth2ResourceServerConfigurer::jwt).cors().and()
                .authorizeRequests(customizer -> customizer
                        // Only authenticated requests can access your protected APIs
                        // e.g. `http://localhost:3000/` and `http://localhost:3000/profile`.
                        .mvcMatchers("/", "/secret").authenticated()
                        // Anyone can access the public profile.
                        .mvcMatchers("/profile").permitAll()
                );
        return http.build();
    }
}

Add a controller to provide the protected and public APIs:

// path/to/project/src/main/java/io/auth/springboot/sample/controller/ProtectedController.java
package io.auth.springboot.sample.controller;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

// Only allow all origins for the sample.
// (Production applications should configure CORS carefully.)
@CrossOrigin(origins = "*")
@RestController
public class ProtectedController {
    @GetMapping("/")
    public String protectedRoot() {
        return "Protected root.";
    }
    @GetMapping("/secret")
    public String protectedSecret() {
        return "Protected secret.";
    }
    @GetMapping("/profile")
    public String publicProfile() {
        return "Public profile.";
    }
}

Build and run your Spring Boot web application, e.g. execute the bootRun Gradle task.

Linux or macOS

./gradlew bootRun

Windows

gradlew.bat bootRun

Request your protected API with the Access Token as the Bearer token in the Authorization header, e.g. execute the curl command.

curl --include 'http://localhost:3000/secret' \
--header 'Authorization: Bearer <your-access-token>'

If succeeded, you will get a response with 200 status:

HTTP/1.1 200

...

Otherwise, you will get a response with 401 status like this:

HTTP/1.1 401

...

WWW-Authenticate: Bearer error="invalid_token", error_description="An error occurred while attempting to decode the Jwt: Signed JWT rejected: Invalid signature", error_uri="https://tools.ietf.org/html/rfc6750#section-3.1"

Get issuer and JWKS URI

All tokens are issued by the , and signed with (See for more details).

By default, your Auth's issuer and JWKS URI are https://<your-auth-domain> and .

Configure application

Provide audience validator

Configure Spring Security

Add APIs

Access protected API

​
Spring Initializr
​
Spring Security OAuth 2.0 Resource Server
Spring Security Architecture
​
issuer
JWK
JWS
https://nightly-accounts-api.complyment.com/.well-known/jwks.json
​
​
​
​
​