io.scalecube.services.security.ServiceTokenAuthenticator Maven / Gradle / Ivy
The newest version!
package io.scalecube.services.security;
import io.scalecube.security.tokens.jwt.JwtToken;
import io.scalecube.security.tokens.jwt.JwtTokenResolver;
import io.scalecube.security.tokens.jwt.JwtUnavailableException;
import io.scalecube.services.auth.Authenticator;
import io.scalecube.services.auth.Principal;
import io.scalecube.services.auth.ServicePrincipal;
import java.time.Duration;
import java.util.Arrays;
import java.util.stream.Collectors;
import reactor.core.publisher.Mono;
import reactor.util.retry.Retry;
/**
* Service authenticator based on JWT token. Being used to verify service identity that establishing
* session to the system. JWT token must have claims: {@code role} and {@code permissions}.
*/
public class ServiceTokenAuthenticator implements Authenticator {
private final JwtTokenResolver tokenResolver;
private final Retry retryStrategy;
/**
* Constructor with defaults.
*
* @param tokenResolver token resolver
*/
public ServiceTokenAuthenticator(JwtTokenResolver tokenResolver) {
this(tokenResolver, 5, Duration.ofSeconds(3));
}
/**
* Constructor.
*
* @param tokenResolver token resolver
* @param retryMaxAttempts max number of retry attempts
* @param retryFixedDelay delay between retry attempts
*/
public ServiceTokenAuthenticator(
JwtTokenResolver tokenResolver, int retryMaxAttempts, Duration retryFixedDelay) {
this.tokenResolver = tokenResolver;
this.retryStrategy =
Retry.fixedDelay(retryMaxAttempts, retryFixedDelay)
.filter(ex -> ex instanceof JwtUnavailableException);
}
@Override
public Mono authenticate(byte[] credentials) {
return Mono.fromFuture(tokenResolver.resolve(new String(credentials)))
.retryWhen(retryStrategy)
.map(JwtToken::payload)
.map(
payload -> {
final var role = (String) payload.get("role");
if (role == null) {
throw new IllegalArgumentException("Wrong token: role claim is missing");
}
final var permissionsClaim = (String) payload.get("permissions");
if (permissionsClaim == null) {
throw new IllegalArgumentException("Wrong token: permissions claim is missing");
}
final var permissions =
Arrays.stream(permissionsClaim.split(","))
.map(String::trim)
.filter(s -> !s.isBlank())
.collect(Collectors.toSet());
return new ServicePrincipal(role, permissions);
});
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy