1
0
mirror of synced 2026-08-05 17:57:15 +00:00

Add Factory Authority When Authentication Succeeds

Issue gh-17933
This commit is contained in:
Josh Cummings
2025-09-19 09:26:41 -06:00
parent 9eaadcc70d
commit e8accd0499
10 changed files with 102 additions and 14 deletions
@@ -17,14 +17,18 @@
package org.springframework.security.config.annotation.web.configurers;
import jakarta.servlet.http.HttpServletRequest;
import org.jspecify.annotations.Nullable;
import org.springframework.context.ApplicationContext;
import org.springframework.security.authentication.AuthenticationDetailsSource;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.config.Customizer;
import org.springframework.security.config.annotation.web.HttpSecurityBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.AuthenticationUserDetailsService;
import org.springframework.security.core.userdetails.UserDetailsByNameServiceWrapper;
import org.springframework.security.core.userdetails.UserDetailsService;
@@ -37,6 +41,7 @@ import org.springframework.security.web.authentication.preauth.x509.SubjectDnX50
import org.springframework.security.web.authentication.preauth.x509.X509AuthenticationFilter;
import org.springframework.security.web.authentication.preauth.x509.X509PrincipalExtractor;
import org.springframework.security.web.context.RequestAttributeSecurityContextRepository;
import org.springframework.security.web.util.matcher.AnyRequestMatcher;
/**
* Adds X509 based pre authentication to an application. Since validating the certificate
@@ -177,8 +182,12 @@ public final class X509Configurer<H extends HttpSecurityBuilder<H>>
public void init(H http) {
PreAuthenticatedAuthenticationProvider authenticationProvider = new PreAuthenticatedAuthenticationProvider();
authenticationProvider.setPreAuthenticatedUserDetailsService(getAuthenticationUserDetailsService(http));
http.authenticationProvider(authenticationProvider)
http.authenticationProvider(new AuthorityGrantingAuthenticationProvider(authenticationProvider))
.setSharedObject(AuthenticationEntryPoint.class, new Http403ForbiddenEntryPoint());
ExceptionHandlingConfigurer<H> exceptions = http.getConfigurer(ExceptionHandlingConfigurer.class);
if (exceptions != null) {
exceptions.defaultAuthenticationEntryPointFor(new Http403ForbiddenEntryPoint(), AnyRequestMatcher.INSTANCE);
}
}
@Override
@@ -225,4 +234,31 @@ public final class X509Configurer<H extends HttpSecurityBuilder<H>>
return context.getBeanProvider(type).getIfUnique();
}
private static final class AuthorityGrantingAuthenticationProvider implements AuthenticationProvider {
private final AuthenticationProvider delegate;
private AuthorityGrantingAuthenticationProvider(AuthenticationProvider delegate) {
this.delegate = delegate;
}
@Override
public @Nullable Authentication authenticate(Authentication authentication) throws AuthenticationException {
Authentication result = this.delegate.authenticate(authentication);
if (result == null) {
return result;
}
return result
.toBuilder()
.authorities((a) -> a.add(new SimpleGrantedAuthority("FACTOR_X509")))
.build();
}
@Override
public boolean supports(Class<?> authentication) {
return true;
}
}
}