Browse Source

Refactor AuthenticationDetailsSource support

- BearerTokenAuthenticationFilter exposes this directly, simplifying
configuration and removing a package tangle

Closes gh-9576
Josh Cummings 4 years ago
parent
commit
7ded671858

+ 1 - 29
config/src/main/java/org/springframework/security/config/annotation/web/configurers/oauth2/server/resource/OAuth2ResourceServerConfigurer.java

@@ -39,7 +39,6 @@ import org.springframework.security.oauth2.core.OAuth2AuthenticationException;
 import org.springframework.security.oauth2.jwt.Jwt;
 import org.springframework.security.oauth2.jwt.JwtDecoder;
 import org.springframework.security.oauth2.jwt.NimbusJwtDecoder;
-import org.springframework.security.oauth2.server.resource.authentication.BearerTokenAuthenticationConverter;
 import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationConverter;
 import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationProvider;
 import org.springframework.security.oauth2.server.resource.authentication.OpaqueTokenAuthenticationProvider;
@@ -52,7 +51,6 @@ import org.springframework.security.oauth2.server.resource.web.DefaultBearerToke
 import org.springframework.security.oauth2.server.resource.web.access.BearerTokenAccessDeniedHandler;
 import org.springframework.security.web.AuthenticationEntryPoint;
 import org.springframework.security.web.access.AccessDeniedHandler;
-import org.springframework.security.web.authentication.AuthenticationConverter;
 import org.springframework.security.web.util.matcher.AndRequestMatcher;
 import org.springframework.security.web.util.matcher.MediaTypeRequestMatcher;
 import org.springframework.security.web.util.matcher.NegatedRequestMatcher;
@@ -80,8 +78,6 @@ import org.springframework.web.accept.HeaderContentNegotiationStrategy;
  * authentication failures are handled
  * <li>{@link #bearerTokenResolver(BearerTokenResolver)} - customizes how to resolve a
  * bearer token from the request</li>
- * <li>{@link #authenticationConverter(AuthenticationConverter)}</li> - customizes how to
- * convert a bearer token authentication from the request
  * <li>{@link #jwt(Customizer)} - enables Jwt-encoded bearer token support</li>
  * <li>{@link #opaqueToken(Customizer)} - enables opaque bearer token support</li>
  * </ul>
@@ -163,8 +159,6 @@ public final class OAuth2ResourceServerConfigurer<H extends HttpSecurityBuilder<
 
 	private BearerTokenRequestMatcher requestMatcher = new BearerTokenRequestMatcher();
 
-	private AuthenticationConverter authenticationConverter;
-
 	public OAuth2ResourceServerConfigurer(ApplicationContext context) {
 		Assert.notNull(context, "context cannot be null");
 		this.context = context;
@@ -195,12 +189,6 @@ public final class OAuth2ResourceServerConfigurer<H extends HttpSecurityBuilder<
 		return this;
 	}
 
-	public OAuth2ResourceServerConfigurer<H> authenticationConverter(AuthenticationConverter authenticationConverter) {
-		Assert.notNull(authenticationConverter, "authenticationConverter cannot be null");
-		this.authenticationConverter = authenticationConverter;
-		return this;
-	}
-
 	public JwtConfigurer jwt() {
 		if (this.jwtConfigurer == null) {
 			this.jwtConfigurer = new JwtConfigurer(this.context);
@@ -265,10 +253,8 @@ public final class OAuth2ResourceServerConfigurer<H extends HttpSecurityBuilder<
 			resolver = (request) -> authenticationManager;
 		}
 
-		this.authenticationConverter = getAuthenticationConverter();
-
 		BearerTokenAuthenticationFilter filter = new BearerTokenAuthenticationFilter(resolver);
-		filter.setAuthenticationConverter(this.authenticationConverter);
+		filter.setBearerTokenResolver(bearerTokenResolver);
 		filter.setAuthenticationEntryPoint(this.authenticationEntryPoint);
 		filter = postProcess(filter);
 		http.addFilter(filter);
@@ -362,20 +348,6 @@ public final class OAuth2ResourceServerConfigurer<H extends HttpSecurityBuilder<
 		return this.bearerTokenResolver;
 	}
 
-	AuthenticationConverter getAuthenticationConverter() {
-		if (this.authenticationConverter == null) {
-			if (this.context.getBeanNamesForType(BearerTokenAuthenticationConverter.class).length > 0) {
-				this.authenticationConverter = this.context.getBean(BearerTokenAuthenticationConverter.class);
-			}
-			else {
-				BearerTokenAuthenticationConverter converter = new BearerTokenAuthenticationConverter();
-				converter.setBearerTokenResolver(getBearerTokenResolver());
-				this.authenticationConverter = converter;
-			}
-		}
-		return this.authenticationConverter;
-	}
-
 	public class JwtConfigurer {
 
 		private final ApplicationContext context;

+ 34 - 80
config/src/test/java/org/springframework/security/config/annotation/web/configurers/oauth2/server/resource/OAuth2ResourceServerConfigurerTests.java

@@ -75,11 +75,13 @@ 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.AuthenticationDetailsSource;
 import org.springframework.security.authentication.AuthenticationEventPublisher;
 import org.springframework.security.authentication.AuthenticationManager;
 import org.springframework.security.authentication.AuthenticationManagerResolver;
 import org.springframework.security.authentication.AuthenticationProvider;
 import org.springframework.security.authentication.AuthenticationServiceException;
+import org.springframework.security.config.annotation.ObjectPostProcessor;
 import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
 import org.springframework.security.config.annotation.web.HttpSecurityBuilder;
 import org.springframework.security.config.annotation.web.builders.HttpSecurity;
@@ -109,20 +111,20 @@ import org.springframework.security.oauth2.jwt.JwtDecoder;
 import org.springframework.security.oauth2.jwt.JwtTimestampValidator;
 import org.springframework.security.oauth2.jwt.NimbusJwtDecoder;
 import org.springframework.security.oauth2.jwt.TestJwts;
-import org.springframework.security.oauth2.server.resource.BearerTokenAuthenticationToken;
 import org.springframework.security.oauth2.server.resource.authentication.BearerTokenAuthentication;
-import org.springframework.security.oauth2.server.resource.authentication.BearerTokenAuthenticationConverter;
 import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationConverter;
 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;
+import org.springframework.security.oauth2.server.resource.web.BearerTokenAuthenticationFilter;
 import org.springframework.security.oauth2.server.resource.web.BearerTokenResolver;
 import org.springframework.security.oauth2.server.resource.web.DefaultBearerTokenResolver;
 import org.springframework.security.oauth2.server.resource.web.access.BearerTokenAccessDeniedHandler;
 import org.springframework.security.provisioning.InMemoryUserDetailsManager;
 import org.springframework.security.web.AuthenticationEntryPoint;
+import org.springframework.security.web.SecurityFilterChain;
 import org.springframework.security.web.access.AccessDeniedHandler;
 import org.springframework.security.web.access.AccessDeniedHandlerImpl;
 import org.springframework.test.web.servlet.MockMvc;
@@ -724,68 +726,14 @@ public class OAuth2ResourceServerConfigurerTests {
 	}
 
 	@Test
-	public void getBearerTokenAuthenticationConverterWhenDuplicateConverterBeansAndAnotherOnTheDslThenTheDslOneIsUsed() {
-		BearerTokenAuthenticationConverter converterBean = new BearerTokenAuthenticationConverter();
-		BearerTokenAuthenticationConverter converter = new BearerTokenAuthenticationConverter();
-		GenericWebApplicationContext context = new GenericWebApplicationContext();
-		context.registerBean("converterOne", BearerTokenAuthenticationConverter.class, () -> converterBean);
-		context.registerBean("converterTwo", BearerTokenAuthenticationConverter.class, () -> converterBean);
-		this.spring.context(context).autowire();
-		OAuth2ResourceServerConfigurer oauth2 = new OAuth2ResourceServerConfigurer(context);
-		oauth2.authenticationConverter(converter);
-		assertThat(oauth2.getAuthenticationConverter()).isEqualTo(converter);
-	}
-
-	@Test
-	public void getBearerTokenAuthenticationConverterWhenDuplicateConverterBeansThenWiringException() {
-		assertThatExceptionOfType(BeanCreationException.class).isThrownBy(() -> this.spring
-				.register(MultipleBearerTokenAuthenticationConverterBeansConfig.class, JwtDecoderConfig.class)
-				.autowire()).withRootCauseInstanceOf(NoUniqueBeanDefinitionException.class);
-	}
-
-	@Test
-	public void getBearerTokenAuthenticationConverterWhenConverterBeanAndAnotherOnTheDslThenTheDslOneIsUsed() {
-		BearerTokenAuthenticationConverter converter = new BearerTokenAuthenticationConverter();
-		BearerTokenAuthenticationConverter converterBean = new BearerTokenAuthenticationConverter();
-		GenericWebApplicationContext context = new GenericWebApplicationContext();
-		context.registerBean(BearerTokenAuthenticationConverter.class, () -> converterBean);
-		this.spring.context(context).autowire();
-		OAuth2ResourceServerConfigurer oauth2 = new OAuth2ResourceServerConfigurer(context);
-		oauth2.authenticationConverter(converter);
-		assertThat(oauth2.getAuthenticationConverter()).isEqualTo(converter);
-	}
-
-	@Test
-	public void getBearerTokenAuthenticationConverterWhenNoConverterSpecifiedThenTheDefaultIsUsed() {
-		ApplicationContext context = this.spring.context(new GenericWebApplicationContext()).getContext();
-		OAuth2ResourceServerConfigurer oauth2 = new OAuth2ResourceServerConfigurer(context);
-		assertThat(oauth2.getAuthenticationConverter()).isInstanceOf(BearerTokenAuthenticationConverter.class);
-	}
-
-	@Test
-	public void getBearerTokenAuthenticationConverterWhenConverterBeanRegisteredThenBeanIsUsed() {
-		BearerTokenAuthenticationConverter converterBean = new BearerTokenAuthenticationConverter();
-		GenericWebApplicationContext context = new GenericWebApplicationContext();
-		context.registerBean(BearerTokenAuthenticationConverter.class, () -> converterBean);
-		this.spring.context(context).autowire();
-		OAuth2ResourceServerConfigurer oauth2 = new OAuth2ResourceServerConfigurer(context);
-		assertThat(oauth2.getAuthenticationConverter()).isEqualTo(converterBean);
-
-	}
-
-	@Test
-	public void getBearerTokenAuthenticationConverterWhenOnlyResolverBeanRegisteredThenUseTheResolver() {
-		HttpServletRequest servletRequest = mock(HttpServletRequest.class);
-		BearerTokenResolver resolverBean = (request) -> "bearer customToken";
-		GenericWebApplicationContext context = new GenericWebApplicationContext();
-		context.registerBean(BearerTokenResolver.class, () -> resolverBean);
-		this.spring.context(context).autowire();
-		OAuth2ResourceServerConfigurer oauth2 = new OAuth2ResourceServerConfigurer(context);
-		BearerTokenAuthenticationToken bearerTokenAuthenticationToken = (BearerTokenAuthenticationToken) oauth2
-				.getAuthenticationConverter().convert(servletRequest);
-		String token = bearerTokenAuthenticationToken.getToken();
-		assertThat(token).isEqualTo("bearer customToken");
-
+	public void requestWhenCustomAuthenticationDetailsSourceThenUsed() throws Exception {
+		this.spring.register(CustomAuthenticationDetailsSource.class, JwtDecoderConfig.class, BasicController.class)
+				.autowire();
+		JwtDecoder decoder = this.spring.getContext().getBean(JwtDecoder.class);
+		given(decoder.decode(anyString())).willReturn(JWT);
+		this.mvc.perform(get("/authenticated").with(bearerToken(JWT_TOKEN))).andExpect(status().isOk())
+				.andExpect(content().string(JWT_SUBJECT));
+		verifyBean(AuthenticationDetailsSource.class).buildDetails(any());
 	}
 
 	@Test
@@ -1940,29 +1888,35 @@ public class OAuth2ResourceServerConfigurerTests {
 	}
 
 	@EnableWebSecurity
-	static class MultipleBearerTokenAuthenticationConverterBeansConfig extends WebSecurityConfigurerAdapter {
+	static class CustomAuthenticationDetailsSource {
 
-		@Override
-		protected void configure(HttpSecurity http) throws Exception {
-			// @formatter:off
-			http
-				.oauth2ResourceServer()
-					.jwt();
-			// @formatter:on
-		}
+		AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource = mock(
+				AuthenticationDetailsSource.class);
 
 		@Bean
-		BearerTokenAuthenticationConverter converterOne() {
-			BearerTokenAuthenticationConverter converter = new BearerTokenAuthenticationConverter();
-			return converter;
+		SecurityFilterChain web(HttpSecurity http) throws Exception {
+			// @formatter:off
+			http
+				.authorizeRequests((authorize) -> authorize
+					.anyRequest().authenticated()
+				)
+				.oauth2ResourceServer((oauth2) -> oauth2
+					.jwt(withDefaults())
+					.withObjectPostProcessor(new ObjectPostProcessor<BearerTokenAuthenticationFilter>() {
+						@Override
+						public BearerTokenAuthenticationFilter postProcess(BearerTokenAuthenticationFilter object) {
+							object.setAuthenticationDetailsSource(CustomAuthenticationDetailsSource.this.authenticationDetailsSource);
+							return object;
+						}
+					})
+				);
+			return http.build();
 		}
 
 		@Bean
-		BearerTokenAuthenticationConverter converterTwo() {
-			BearerTokenAuthenticationConverter converter = new BearerTokenAuthenticationConverter();
-			return converter;
+		AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource() {
+			return this.authenticationDetailsSource;
 		}
-
 	}
 
 	@EnableWebSecurity

+ 0 - 77
oauth2/oauth2-resource-server/src/main/java/org/springframework/security/oauth2/server/resource/authentication/BearerTokenAuthenticationConverter.java

@@ -1,77 +0,0 @@
-/*
- * Copyright 2002-2021 the original author or authors.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      https://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.springframework.security.oauth2.server.resource.authentication;
-
-import javax.servlet.http.HttpServletRequest;
-
-import org.springframework.security.authentication.AuthenticationDetailsSource;
-import org.springframework.security.oauth2.server.resource.BearerTokenAuthenticationToken;
-import org.springframework.security.oauth2.server.resource.web.BearerTokenResolver;
-import org.springframework.security.oauth2.server.resource.web.DefaultBearerTokenResolver;
-import org.springframework.security.web.authentication.AuthenticationConverter;
-import org.springframework.security.web.authentication.WebAuthenticationDetailsSource;
-import org.springframework.util.Assert;
-
-/**
- * Converts from a HttpServletRequest to {@link BearerTokenAuthenticationToken} that can
- * be authenticated. Null authentication possible if there was no Authorization header
- * with Bearer Token.
- *
- * @author Jeongjin Kim
- * @since 5.5
- */
-public final class BearerTokenAuthenticationConverter implements AuthenticationConverter {
-
-	private BearerTokenResolver bearerTokenResolver = new DefaultBearerTokenResolver();
-
-	private AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource = new WebAuthenticationDetailsSource();
-
-	@Override
-	public BearerTokenAuthenticationToken convert(HttpServletRequest request) {
-		String token = this.bearerTokenResolver.resolve(request);
-
-		if (token == null) {
-			return null;
-		}
-
-		BearerTokenAuthenticationToken authenticationRequest = new BearerTokenAuthenticationToken(token);
-		authenticationRequest.setDetails(this.authenticationDetailsSource.buildDetails(request));
-		return authenticationRequest;
-	}
-
-	/**
-	 * Set the {@link BearerTokenResolver} to use. Defaults to
-	 * {@link DefaultBearerTokenResolver}.
-	 * @param bearerTokenResolver the {@code BearerTokenResolver} to use
-	 */
-	public void setBearerTokenResolver(BearerTokenResolver bearerTokenResolver) {
-		Assert.notNull(bearerTokenResolver, "bearerTokenResolver cannot be null");
-		this.bearerTokenResolver = bearerTokenResolver;
-	}
-
-	/**
-	 * Set the {@link AuthenticationDetailsSource} to use. Defaults to
-	 * {@link WebAuthenticationDetailsSource}.
-	 * @param authenticationDetailsSource the {@code AuthenticationDetailsSource} to use
-	 */
-	public void setAuthenticationDetailsSource(
-			AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource) {
-		Assert.notNull(authenticationDetailsSource, "authenticationDetailsSource cannot be null");
-		this.authenticationDetailsSource = authenticationDetailsSource;
-	}
-
-}

+ 27 - 26
oauth2/oauth2-resource-server/src/main/java/org/springframework/security/oauth2/server/resource/web/BearerTokenAuthenticationFilter.java

@@ -24,6 +24,7 @@ import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
 
 import org.springframework.core.log.LogMessage;
+import org.springframework.security.authentication.AuthenticationDetailsSource;
 import org.springframework.security.authentication.AuthenticationManager;
 import org.springframework.security.authentication.AuthenticationManagerResolver;
 import org.springframework.security.authentication.AuthenticationServiceException;
@@ -31,12 +32,12 @@ import org.springframework.security.core.Authentication;
 import org.springframework.security.core.AuthenticationException;
 import org.springframework.security.core.context.SecurityContext;
 import org.springframework.security.core.context.SecurityContextHolder;
+import org.springframework.security.oauth2.core.OAuth2AuthenticationException;
 import org.springframework.security.oauth2.server.resource.BearerTokenAuthenticationToken;
-import org.springframework.security.oauth2.server.resource.authentication.BearerTokenAuthenticationConverter;
 import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationProvider;
 import org.springframework.security.web.AuthenticationEntryPoint;
-import org.springframework.security.web.authentication.AuthenticationConverter;
 import org.springframework.security.web.authentication.AuthenticationFailureHandler;
+import org.springframework.security.web.authentication.WebAuthenticationDetailsSource;
 import org.springframework.util.Assert;
 import org.springframework.web.filter.OncePerRequestFilter;
 
@@ -51,6 +52,7 @@ import org.springframework.web.filter.OncePerRequestFilter;
  * @author Josh Cummings
  * @author Vedran Pavic
  * @author Joe Grandja
+ * @author Jeongjin Kim
  * @since 5.1
  * @see <a href="https://tools.ietf.org/html/rfc6750" target="_blank">The OAuth 2.0
  * Authorization Framework: Bearer Token Usage</a>
@@ -69,7 +71,9 @@ public final class BearerTokenAuthenticationFilter extends OncePerRequestFilter
 		this.authenticationEntryPoint.commence(request, response, exception);
 	};
 
-	private AuthenticationConverter authenticationConverter = new BearerTokenAuthenticationConverter();
+	private BearerTokenResolver bearerTokenResolver = new DefaultBearerTokenResolver();
+
+	private AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource = new WebAuthenticationDetailsSource();
 
 	/**
 	 * Construct a {@code BearerTokenAuthenticationFilter} using the provided parameter(s)
@@ -103,21 +107,24 @@ public final class BearerTokenAuthenticationFilter extends OncePerRequestFilter
 	@Override
 	protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)
 			throws ServletException, IOException {
-		Authentication authenticationRequest;
+		String token;
 		try {
-			authenticationRequest = this.authenticationConverter.convert(request);
+			token = this.bearerTokenResolver.resolve(request);
 		}
-		catch (AuthenticationException invalid) {
+		catch (OAuth2AuthenticationException invalid) {
 			this.logger.trace("Sending to authentication entry point since failed to resolve bearer token", invalid);
 			this.authenticationEntryPoint.commence(request, response, invalid);
 			return;
 		}
-		if (authenticationRequest == null) {
+		if (token == null) {
 			this.logger.trace("Did not process request since did not find bearer token");
 			filterChain.doFilter(request, response);
 			return;
 		}
 
+		BearerTokenAuthenticationToken authenticationRequest = new BearerTokenAuthenticationToken(token);
+		authenticationRequest.setDetails(this.authenticationDetailsSource.buildDetails(request));
+
 		try {
 			AuthenticationManager authenticationManager = this.authenticationManagerResolver.resolve(request);
 			Authentication authenticationResult = authenticationManager.authenticate(authenticationRequest);
@@ -140,28 +147,10 @@ public final class BearerTokenAuthenticationFilter extends OncePerRequestFilter
 	 * Set the {@link BearerTokenResolver} to use. Defaults to
 	 * {@link DefaultBearerTokenResolver}.
 	 * @param bearerTokenResolver the {@code BearerTokenResolver} to use
-	 * @deprecated Instead, use {@link BearerTokenAuthenticationConverter} explicitly
-	 * @see BearerTokenAuthenticationConverter
 	 */
-	@Deprecated
 	public void setBearerTokenResolver(BearerTokenResolver bearerTokenResolver) {
 		Assert.notNull(bearerTokenResolver, "bearerTokenResolver cannot be null");
-		Assert.isTrue(this.authenticationConverter instanceof BearerTokenAuthenticationConverter,
-				"bearerTokenResolver and authenticationConverter cannot both be customized in this filter. "
-						+ "Since you've customized the authenticationConverter, "
-						+ "please consider configuring the bearerTokenResolver there.");
-		((BearerTokenAuthenticationConverter) this.authenticationConverter).setBearerTokenResolver(bearerTokenResolver);
-	}
-
-	/**
-	 * Set the {@link AuthenticationConverter} to use. Defaults to
-	 * {@link BearerTokenAuthenticationConverter}.
-	 * @param authenticationConverter the {@code AuthenticationConverter} to use
-	 * @since 5.5
-	 */
-	public void setAuthenticationConverter(AuthenticationConverter authenticationConverter) {
-		Assert.notNull(authenticationConverter, "authenticationConverter cannot be null");
-		this.authenticationConverter = authenticationConverter;
+		this.bearerTokenResolver = bearerTokenResolver;
 	}
 
 	/**
@@ -185,4 +174,16 @@ public final class BearerTokenAuthenticationFilter extends OncePerRequestFilter
 		this.authenticationFailureHandler = authenticationFailureHandler;
 	}
 
+	/**
+	 * Set the {@link AuthenticationDetailsSource} to use. Defaults to
+	 * {@link WebAuthenticationDetailsSource}.
+	 * @param authenticationDetailsSource the {@code AuthenticationConverter} to use
+	 * @since 5.5
+	 */
+	public void setAuthenticationDetailsSource(
+			AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource) {
+		Assert.notNull(authenticationDetailsSource, "authenticationDetailsSource cannot be null");
+		this.authenticationDetailsSource = authenticationDetailsSource;
+	}
+
 }

+ 0 - 87
oauth2/oauth2-resource-server/src/test/java/org/springframework/security/oauth2/server/resource/authentication/BearerTokenAuthenticationConverterTests.java

@@ -1,87 +0,0 @@
-/*
- * Copyright 2002-2021 the original author or authors.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      https://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.springframework.security.oauth2.server.resource.authentication;
-
-import javax.servlet.http.HttpServletRequest;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.junit.MockitoJUnitRunner;
-
-import org.springframework.http.HttpHeaders;
-import org.springframework.security.oauth2.server.resource.BearerTokenAuthenticationToken;
-
-import static org.assertj.core.api.Assertions.assertThat;
-import static org.assertj.core.api.Assertions.assertThatIllegalArgumentException;
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-/**
- * Tests for {@link BearerTokenAuthenticationConverter}
- *
- * @author Jeongjin Kim
- * @since 5.5
- */
-@RunWith(MockitoJUnitRunner.class)
-public class BearerTokenAuthenticationConverterTests {
-
-	private BearerTokenAuthenticationConverter converter;
-
-	@Before
-	public void setup() {
-		this.converter = new BearerTokenAuthenticationConverter();
-	}
-
-	@Test
-	public void setBearerTokenResolverWithNullThenThrowsException() {
-		// @formatter:off
-		assertThatIllegalArgumentException()
-				.isThrownBy(() -> this.converter.setBearerTokenResolver(null))
-				.withMessageContaining("bearerTokenResolver cannot be null");
-		// @formatter:on
-	}
-
-	@Test
-	public void setAuthenticationDetailsSourceWithNullThenThrowsException() {
-		// @formatter:off
-		assertThatIllegalArgumentException()
-				.isThrownBy(() -> this.converter.setAuthenticationDetailsSource(null))
-				.withMessageContaining("authenticationDetailsSource cannot be null");
-		// @formatter:on
-	}
-
-	@Test
-	public void convertWhenNoBearerTokenHeaderThenNull() {
-		HttpServletRequest request = mock(HttpServletRequest.class);
-
-		BearerTokenAuthenticationToken convert = this.converter.convert(request);
-
-		assertThat(convert).isNull();
-	}
-
-	@Test
-	public void convertWhenBearerTokenThenBearerTokenAuthenticationToken() {
-		HttpServletRequest request = mock(HttpServletRequest.class);
-		given(request.getHeader(HttpHeaders.AUTHORIZATION)).willReturn("Bearer token");
-
-		BearerTokenAuthenticationToken token = this.converter.convert(request);
-
-		assertThat(token.getToken()).isEqualTo("token");
-	}
-
-}

+ 16 - 2
oauth2/oauth2-resource-server/src/test/java/org/springframework/security/oauth2/server/resource/web/BearerTokenAuthenticationFilterTests.java

@@ -32,6 +32,7 @@ import org.springframework.http.HttpStatus;
 import org.springframework.mock.web.MockFilterChain;
 import org.springframework.mock.web.MockHttpServletRequest;
 import org.springframework.mock.web.MockHttpServletResponse;
+import org.springframework.security.authentication.AuthenticationDetailsSource;
 import org.springframework.security.authentication.AuthenticationManager;
 import org.springframework.security.authentication.AuthenticationManagerResolver;
 import org.springframework.security.authentication.AuthenticationServiceException;
@@ -73,6 +74,9 @@ public class BearerTokenAuthenticationFilterTests {
 	@Mock
 	BearerTokenResolver bearerTokenResolver;
 
+	@Mock
+	AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource;
+
 	MockHttpServletRequest request;
 
 	MockHttpServletResponse response;
@@ -167,6 +171,15 @@ public class BearerTokenAuthenticationFilterTests {
 				.isThrownBy(() -> filter.doFilter(this.request, this.response, this.filterChain));
 	}
 
+	@Test
+	public void doFilterWhenCustomAuthenticationDetailsSourceThenUses() throws ServletException, IOException {
+		given(this.bearerTokenResolver.resolve(this.request)).willReturn("token");
+		BearerTokenAuthenticationFilter filter = addMocks(
+				new BearerTokenAuthenticationFilter(this.authenticationManager));
+		filter.doFilter(this.request, this.response, this.filterChain);
+		verify(this.authenticationDetailsSource).buildDetails(this.request);
+	}
+
 	@Test
 	public void setAuthenticationEntryPointWhenNullThenThrowsException() {
 		BearerTokenAuthenticationFilter filter = new BearerTokenAuthenticationFilter(this.authenticationManager);
@@ -192,8 +205,8 @@ public class BearerTokenAuthenticationFilterTests {
 		// @formatter:off
 		BearerTokenAuthenticationFilter filter = new BearerTokenAuthenticationFilter(this.authenticationManager);
 		assertThatIllegalArgumentException()
-				.isThrownBy(() -> filter.setAuthenticationConverter(null))
-				.withMessageContaining("authenticationConverter cannot be null");
+				.isThrownBy(() -> filter.setAuthenticationDetailsSource(null))
+				.withMessageContaining("authenticationDetailsSource cannot be null");
 		// @formatter:on
 	}
 
@@ -218,6 +231,7 @@ public class BearerTokenAuthenticationFilterTests {
 	private BearerTokenAuthenticationFilter addMocks(BearerTokenAuthenticationFilter filter) {
 		filter.setAuthenticationEntryPoint(this.authenticationEntryPoint);
 		filter.setBearerTokenResolver(this.bearerTokenResolver);
+		filter.setAuthenticationDetailsSource(this.authenticationDetailsSource);
 		return filter;
 	}