AuthenticationEventPublisher Bean Lookup

Issue gh-7793
Fixes gh-7515
This commit is contained in:
Josh Cummings 2020-01-09 13:41:46 -07:00
parent fc9b97c94a
commit 5579846263
3 changed files with 88 additions and 3 deletions

View File

@ -26,6 +26,7 @@ import java.util.Set;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.aop.TargetSource;
import org.springframework.aop.framework.Advised;
import org.springframework.aop.target.LazyInitTargetSource;
@ -36,6 +37,7 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.core.annotation.Order;
import org.springframework.core.io.support.SpringFactoriesLoader;
import org.springframework.security.authentication.AuthenticationEventPublisher;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.AuthenticationTrustResolver;
import org.springframework.security.authentication.AuthenticationTrustResolverImpl;
@ -194,8 +196,7 @@ public abstract class WebSecurityConfigurerAdapter implements
return http;
}
DefaultAuthenticationEventPublisher eventPublisher = objectPostProcessor
.postProcess(new DefaultAuthenticationEventPublisher());
AuthenticationEventPublisher eventPublisher = getAuthenticationEventPublisher();
localConfigureAuthenticationBldr.authenticationEventPublisher(eventPublisher);
AuthenticationManager authenticationManager = authenticationManager();
@ -407,6 +408,13 @@ public abstract class WebSecurityConfigurerAdapter implements
this.authenticationConfiguration = authenticationConfiguration;
}
private AuthenticationEventPublisher getAuthenticationEventPublisher() {
if (this.context.getBeanNamesForType(AuthenticationEventPublisher.class).length > 0) {
return this.context.getBean(AuthenticationEventPublisher.class);
}
return this.objectPostProcessor.postProcess(new DefaultAuthenticationEventPublisher());
}
/**
* Creates the shared objects
*

View File

@ -33,6 +33,7 @@ import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.annotation.AnnotationAwareOrderComparator;
import org.springframework.core.annotation.Order;
import org.springframework.security.authentication.AuthenticationEventPublisher;
import org.springframework.security.authentication.AuthenticationTrustResolver;
import org.springframework.security.authentication.event.AuthenticationSuccessEvent;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
@ -40,9 +41,11 @@ 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.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.test.SpringTestRule;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.userdetails.PasswordEncodedUser;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.web.accept.ContentNegotiationStrategy;
@ -51,8 +54,11 @@ import org.springframework.web.filter.OncePerRequestFilter;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.ThrowableAssert.catchThrowable;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.httpBasic;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.header;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
@ -364,4 +370,32 @@ public class WebSecurityConfigurerAdapterTests {
@Order
static class LowestPriorityWebSecurityConfig extends WebSecurityConfigurerAdapter {
}
// gh-7515
@Test
public void performWhenUsingAuthenticationEventPublisherBeanThenUses() throws Exception {
this.spring.register(CustomAuthenticationEventPublisherBean.class).autowire();
AuthenticationEventPublisher authenticationEventPublisher =
this.spring.getContext().getBean(AuthenticationEventPublisher.class);
this.mockMvc.perform(get("/")
.with(httpBasic("user", "password")));
verify(authenticationEventPublisher).publishAuthenticationSuccess(any(Authentication.class));
}
@EnableWebSecurity
static class CustomAuthenticationEventPublisherBean extends WebSecurityConfigurerAdapter {
@Bean
@Override
public UserDetailsService userDetailsService() {
return new InMemoryUserDetailsManager(PasswordEncodedUser.user());
}
@Bean
public AuthenticationEventPublisher authenticationEventPublisher() {
return mock(AuthenticationEventPublisher.class);
}
}
}

View File

@ -73,6 +73,7 @@ import org.springframework.http.ResponseEntity;
import org.springframework.mock.web.MockHttpServletRequest;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.security.authentication.AbstractAuthenticationToken;
import org.springframework.security.authentication.AuthenticationEventPublisher;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.AuthenticationManagerResolver;
import org.springframework.security.authentication.AuthenticationProvider;
@ -88,6 +89,7 @@ import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.oauth2.core.DefaultOAuth2AuthenticatedPrincipal;
import org.springframework.security.oauth2.core.OAuth2AuthenticationException;
import org.springframework.security.oauth2.core.OAuth2Error;
import org.springframework.security.oauth2.core.OAuth2TokenValidator;
import org.springframework.security.oauth2.core.OAuth2TokenValidatorResult;
@ -99,8 +101,8 @@ import org.springframework.security.oauth2.jwt.JwtTimestampValidator;
import org.springframework.security.oauth2.jwt.NimbusJwtDecoder;
import org.springframework.security.oauth2.server.resource.authentication.BearerTokenAuthentication;
import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationConverter;
import org.springframework.security.oauth2.server.resource.authentication.JwtIssuerAuthenticationManagerResolver;
import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationToken;
import org.springframework.security.oauth2.server.resource.authentication.JwtIssuerAuthenticationManagerResolver;
import org.springframework.security.oauth2.server.resource.introspection.NimbusOpaqueTokenIntrospector;
import org.springframework.security.oauth2.server.resource.introspection.OpaqueTokenIntrospector;
import org.springframework.security.oauth2.server.resource.web.BearerTokenAuthenticationEntryPoint;
@ -1091,6 +1093,22 @@ public class OAuth2ResourceServerConfigurerTests {
.andExpect(invalidTokenHeader("algorithm"));
}
// gh-7793
@Test
public void requestWhenUsingCustomAuthenticationEventPublisherThenUses() throws Exception{
this.spring.register(CustomAuthenticationEventPublisher.class).autowire();
when(bean(JwtDecoder.class).decode(anyString()))
.thenThrow(new JwtException("problem"));
this.mvc.perform(get("/").with(bearerToken("token")));
verifyBean(AuthenticationEventPublisher.class)
.publishAuthenticationFailure(
any(OAuth2AuthenticationException.class),
any(Authentication.class));
}
@Test
public void getWhenCustomJwtAuthenticationManagerThenUsed() throws Exception {
this.spring.register(JwtAuthenticationManagerConfig.class, BasicController.class).autowire();
@ -2015,6 +2033,31 @@ public class OAuth2ResourceServerConfigurerTests {
}
}
@EnableWebSecurity
static class CustomAuthenticationEventPublisher extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
// @formatter:off
http
.authorizeRequests()
.anyRequest().authenticated()
.and()
.oauth2ResourceServer()
.jwt();
// @formatter:on
}
@Bean
JwtDecoder jwtDecoder() {
return mock(JwtDecoder.class);
}
@Bean
AuthenticationEventPublisher authenticationEventPublisher() {
return mock(AuthenticationEventPublisher.class);
}
}
@EnableWebSecurity
static class OpaqueTokenConfig extends WebSecurityConfigurerAdapter {
@Override