浏览代码

Allow customizing OIDC Provider Configuration Response

Closes gh-616
Joe Grandja 3 年之前
父节点
当前提交
0994a1e1e1

+ 27 - 2
docs/src/docs/asciidoc/protocol-endpoints.adoc

@@ -198,9 +198,34 @@ The JWK Set endpoint is configured *only* if a `JWKSource<SecurityContext>` `@Be
 [[oidc-provider-configuration-endpoint]]
 == OpenID Connect 1.0 Provider Configuration Endpoint
 
-`OidcConfigurer` provides support for the https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfig[OpenID Connect 1.0 Provider Configuration endpoint].
+`OidcProviderConfigurationEndpointConfigurer` provides the ability to customize the https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfig[OpenID Connect 1.0 Provider Configuration endpoint].
+It defines an extension point that lets you customize the https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfigurationResponse[OpenID Provider Configuration response].
 
-`OidcConfigurer` configures the `OidcProviderConfigurationEndpointFilter` and registers it with the OAuth2 authorization server `SecurityFilterChain` `@Bean`.
+`OidcProviderConfigurationEndpointConfigurer` provides the following configuration option:
+
+[source,java]
+----
+@Bean
+public SecurityFilterChain authorizationServerSecurityFilterChain(HttpSecurity http) throws Exception {
+	OAuth2AuthorizationServerConfigurer authorizationServerConfigurer =
+		new OAuth2AuthorizationServerConfigurer();
+	http.apply(authorizationServerConfigurer);
+
+	authorizationServerConfigurer
+		.oidc(oidc ->
+			oidc
+				.providerConfigurationEndpoint(providerConfigurationEndpoint ->
+					providerConfigurationEndpoint
+						.providerConfigurationCustomizer(providerConfigurationCustomizer)   <1>
+				)
+		);
+
+	return http.build();
+}
+----
+<1> `providerConfigurationCustomizer()`: The `Consumer` providing access to the `OidcProviderConfiguration.Builder` allowing the ability to customize the claims of the OpenID Provider's configuration.
+
+`OidcProviderConfigurationEndpointConfigurer` configures the `OidcProviderConfigurationEndpointFilter` and registers it with the OAuth2 authorization server `SecurityFilterChain` `@Bean`.
 `OidcProviderConfigurationEndpointFilter` is the `Filter` that returns the https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfigurationResponse[OidcProviderConfiguration response].
 
 [[oidc-user-info-endpoint]]

+ 19 - 32
oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OidcConfigurer.java

@@ -20,13 +20,9 @@ import java.util.LinkedHashMap;
 import java.util.List;
 import java.util.Map;
 
-import org.springframework.http.HttpMethod;
 import org.springframework.security.config.Customizer;
 import org.springframework.security.config.annotation.ObjectPostProcessor;
 import org.springframework.security.config.annotation.web.builders.HttpSecurity;
-import org.springframework.security.oauth2.server.authorization.oidc.web.OidcProviderConfigurationEndpointFilter;
-import org.springframework.security.web.authentication.preauth.AbstractPreAuthenticatedProcessingFilter;
-import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
 import org.springframework.security.web.util.matcher.OrRequestMatcher;
 import org.springframework.security.web.util.matcher.RequestMatcher;
 
@@ -36,9 +32,9 @@ import org.springframework.security.web.util.matcher.RequestMatcher;
  * @author Joe Grandja
  * @since 0.2.0
  * @see OAuth2AuthorizationServerConfigurer#oidc
+ * @see OidcProviderConfigurationEndpointConfigurer
  * @see OidcClientRegistrationEndpointConfigurer
  * @see OidcUserInfoEndpointConfigurer
- * @see OidcProviderConfigurationEndpointFilter
  */
 public final class OidcConfigurer extends AbstractOAuth2Configurer {
 	private final Map<Class<? extends AbstractOAuth2Configurer>, AbstractOAuth2Configurer> configurers = new LinkedHashMap<>();
@@ -49,9 +45,22 @@ public final class OidcConfigurer extends AbstractOAuth2Configurer {
 	 */
 	OidcConfigurer(ObjectPostProcessor<Object> objectPostProcessor) {
 		super(objectPostProcessor);
+		addConfigurer(OidcProviderConfigurationEndpointConfigurer.class, new OidcProviderConfigurationEndpointConfigurer(objectPostProcessor));
 		addConfigurer(OidcUserInfoEndpointConfigurer.class, new OidcUserInfoEndpointConfigurer(objectPostProcessor));
 	}
 
+	/**
+	 * Configures the OpenID Connect 1.0 Provider Configuration Endpoint.
+	 *
+	 * @param providerConfigurationEndpointCustomizer the {@link Customizer} providing access to the {@link OidcProviderConfigurationEndpointConfigurer}
+	 * @return the {@link OidcConfigurer} for further configuration
+	 * @since 0.4.0
+	 */
+	public OidcConfigurer providerConfigurationEndpoint(Customizer<OidcProviderConfigurationEndpointConfigurer> providerConfigurationEndpointCustomizer) {
+		providerConfigurationEndpointCustomizer.customize(getConfigurer(OidcProviderConfigurationEndpointConfigurer.class));
+		return this;
+	}
+
 	/**
 	 * Configures the OpenID Connect Dynamic Client Registration 1.0 Endpoint.
 	 *
@@ -83,39 +92,17 @@ public final class OidcConfigurer extends AbstractOAuth2Configurer {
 
 	@Override
 	void init(HttpSecurity httpSecurity) {
-		OidcUserInfoEndpointConfigurer userInfoEndpointConfigurer =
-				getConfigurer(OidcUserInfoEndpointConfigurer.class);
-		userInfoEndpointConfigurer.init(httpSecurity);
-		OidcClientRegistrationEndpointConfigurer clientRegistrationEndpointConfigurer =
-				getConfigurer(OidcClientRegistrationEndpointConfigurer.class);
-		if (clientRegistrationEndpointConfigurer != null) {
-			clientRegistrationEndpointConfigurer.init(httpSecurity);
-		}
-
 		List<RequestMatcher> requestMatchers = new ArrayList<>();
-		requestMatchers.add(new AntPathRequestMatcher(
-				"/.well-known/openid-configuration", HttpMethod.GET.name()));
-		requestMatchers.add(userInfoEndpointConfigurer.getRequestMatcher());
-		if (clientRegistrationEndpointConfigurer != null) {
-			requestMatchers.add(clientRegistrationEndpointConfigurer.getRequestMatcher());
-		}
+		this.configurers.values().forEach(configurer -> {
+			configurer.init(httpSecurity);
+			requestMatchers.add(configurer.getRequestMatcher());
+		});
 		this.requestMatcher = new OrRequestMatcher(requestMatchers);
 	}
 
 	@Override
 	void configure(HttpSecurity httpSecurity) {
-		OidcUserInfoEndpointConfigurer userInfoEndpointConfigurer =
-				getConfigurer(OidcUserInfoEndpointConfigurer.class);
-		userInfoEndpointConfigurer.configure(httpSecurity);
-		OidcClientRegistrationEndpointConfigurer clientRegistrationEndpointConfigurer =
-				getConfigurer(OidcClientRegistrationEndpointConfigurer.class);
-		if (clientRegistrationEndpointConfigurer != null) {
-			clientRegistrationEndpointConfigurer.configure(httpSecurity);
-		}
-
-		OidcProviderConfigurationEndpointFilter oidcProviderConfigurationEndpointFilter =
-				new OidcProviderConfigurationEndpointFilter();
-		httpSecurity.addFilterBefore(postProcess(oidcProviderConfigurationEndpointFilter), AbstractPreAuthenticatedProcessingFilter.class);
+		this.configurers.values().forEach(configurer -> configurer.configure(httpSecurity));
 	}
 
 	@Override

+ 108 - 0
oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OidcProviderConfigurationEndpointConfigurer.java

@@ -0,0 +1,108 @@
+/*
+ * Copyright 2020-2022 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.authorization.config.annotation.web.configurers;
+
+import java.util.function.Consumer;
+
+import org.springframework.http.HttpMethod;
+import org.springframework.security.config.annotation.ObjectPostProcessor;
+import org.springframework.security.config.annotation.web.builders.HttpSecurity;
+import org.springframework.security.oauth2.server.authorization.oidc.OidcProviderConfiguration;
+import org.springframework.security.oauth2.server.authorization.oidc.web.OidcProviderConfigurationEndpointFilter;
+import org.springframework.security.web.authentication.preauth.AbstractPreAuthenticatedProcessingFilter;
+import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
+import org.springframework.security.web.util.matcher.RequestMatcher;
+
+/**
+ * Configurer for the OpenID Connect 1.0 Provider Configuration Endpoint.
+ *
+ * @author Joe Grandja
+ * @since 0.4.0
+ * @see OidcConfigurer#providerConfigurationEndpoint
+ * @see OidcProviderConfigurationEndpointFilter
+ */
+public final class OidcProviderConfigurationEndpointConfigurer extends AbstractOAuth2Configurer {
+	private RequestMatcher requestMatcher;
+	private Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer;
+	private Consumer<OidcProviderConfiguration.Builder> defaultProviderConfigurationCustomizer;
+
+	/**
+	 * Restrict for internal use only.
+	 */
+	OidcProviderConfigurationEndpointConfigurer(ObjectPostProcessor<Object> objectPostProcessor) {
+		super(objectPostProcessor);
+	}
+
+	/**
+	 * Sets the {@code Consumer} providing access to the {@link OidcProviderConfiguration.Builder}
+	 * allowing the ability to customize the claims of the OpenID Provider's configuration.
+	 *
+	 * @param providerConfigurationCustomizer the {@code Consumer} providing access to the {@link OidcProviderConfiguration.Builder}
+	 * @return the {@link OidcProviderConfigurationEndpointConfigurer} for further configuration
+	 */
+	public OidcProviderConfigurationEndpointConfigurer providerConfigurationCustomizer(
+			Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer) {
+		this.providerConfigurationCustomizer = providerConfigurationCustomizer;
+		return this;
+	}
+
+	void addDefaultProviderConfigurationCustomizer(
+			Consumer<OidcProviderConfiguration.Builder> defaultProviderConfigurationCustomizer) {
+		this.defaultProviderConfigurationCustomizer =
+				this.defaultProviderConfigurationCustomizer == null ?
+						defaultProviderConfigurationCustomizer :
+						this.defaultProviderConfigurationCustomizer.andThen(defaultProviderConfigurationCustomizer);
+	}
+
+	@Override
+	void init(HttpSecurity httpSecurity) {
+		this.requestMatcher = new AntPathRequestMatcher(
+				"/.well-known/openid-configuration", HttpMethod.GET.name());
+	}
+
+	@Override
+	void configure(HttpSecurity httpSecurity) {
+		OidcProviderConfigurationEndpointFilter oidcProviderConfigurationEndpointFilter =
+				new OidcProviderConfigurationEndpointFilter();
+		Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer = getProviderConfigurationCustomizer();
+		if (providerConfigurationCustomizer != null) {
+			oidcProviderConfigurationEndpointFilter.setProviderConfigurationCustomizer(providerConfigurationCustomizer);
+		}
+		httpSecurity.addFilterBefore(postProcess(oidcProviderConfigurationEndpointFilter), AbstractPreAuthenticatedProcessingFilter.class);
+	}
+
+	private Consumer<OidcProviderConfiguration.Builder> getProviderConfigurationCustomizer() {
+		Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer = null;
+		if (this.defaultProviderConfigurationCustomizer != null || this.providerConfigurationCustomizer != null) {
+			if (this.defaultProviderConfigurationCustomizer != null) {
+				providerConfigurationCustomizer = this.defaultProviderConfigurationCustomizer;
+			}
+			if (this.providerConfigurationCustomizer != null) {
+				providerConfigurationCustomizer =
+						providerConfigurationCustomizer == null ?
+								this.providerConfigurationCustomizer :
+								providerConfigurationCustomizer.andThen(this.providerConfigurationCustomizer);
+			}
+		}
+		return providerConfigurationCustomizer;
+	}
+
+	@Override
+	RequestMatcher getRequestMatcher() {
+		return this.requestMatcher;
+	}
+
+}

+ 20 - 4
oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/oidc/web/OidcProviderConfigurationEndpointFilter.java

@@ -39,6 +39,7 @@ import org.springframework.security.oauth2.server.authorization.oidc.http.conver
 import org.springframework.security.oauth2.server.authorization.settings.AuthorizationServerSettings;
 import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
 import org.springframework.security.web.util.matcher.RequestMatcher;
+import org.springframework.util.Assert;
 import org.springframework.web.filter.OncePerRequestFilter;
 import org.springframework.web.util.UriComponentsBuilder;
 
@@ -46,6 +47,7 @@ import org.springframework.web.util.UriComponentsBuilder;
  * A {@code Filter} that processes OpenID Provider Configuration Requests.
  *
  * @author Daniel Garnier-Moiroux
+ * @author Joe Grandja
  * @since 0.1.0
  * @see OidcProviderConfiguration
  * @see AuthorizationServerSettings
@@ -62,6 +64,19 @@ public final class OidcProviderConfigurationEndpointFilter extends OncePerReques
 			HttpMethod.GET.name());
 	private final OidcProviderConfigurationHttpMessageConverter providerConfigurationHttpMessageConverter =
 			new OidcProviderConfigurationHttpMessageConverter();
+	private Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer = (providerConfiguration) -> {};
+
+	/**
+	 * Sets the {@code Consumer} providing access to the {@link OidcProviderConfiguration.Builder}
+	 * allowing the ability to customize the claims of the OpenID Provider's configuration.
+	 *
+	 * @param providerConfigurationCustomizer the {@code Consumer} providing access to the {@link OidcProviderConfiguration.Builder}
+	 * @since 0.4.0
+	 */
+	public void setProviderConfigurationCustomizer(Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer) {
+		Assert.notNull(providerConfigurationCustomizer, "providerConfigurationCustomizer cannot be null");
+		this.providerConfigurationCustomizer = providerConfigurationCustomizer;
+	}
 
 	@Override
 	protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)
@@ -76,7 +91,7 @@ public final class OidcProviderConfigurationEndpointFilter extends OncePerReques
 		String issuer = authorizationServerContext.getIssuer();
 		AuthorizationServerSettings authorizationServerSettings = authorizationServerContext.getAuthorizationServerSettings();
 
-		OidcProviderConfiguration providerConfiguration = OidcProviderConfiguration.builder()
+		OidcProviderConfiguration.Builder providerConfiguration = OidcProviderConfiguration.builder()
 				.issuer(issuer)
 				.authorizationEndpoint(asUrl(issuer, authorizationServerSettings.getAuthorizationEndpoint()))
 				.tokenEndpoint(asUrl(issuer, authorizationServerSettings.getTokenEndpoint()))
@@ -93,12 +108,13 @@ public final class OidcProviderConfigurationEndpointFilter extends OncePerReques
 				.tokenIntrospectionEndpointAuthenticationMethods(clientAuthenticationMethods())
 				.subjectType("public")
 				.idTokenSigningAlgorithm(SignatureAlgorithm.RS256.getName())
-				.scope(OidcScopes.OPENID)
-				.build();
+				.scope(OidcScopes.OPENID);
+
+		this.providerConfigurationCustomizer.accept(providerConfiguration);
 
 		ServletServerHttpResponse httpResponse = new ServletServerHttpResponse(response);
 		this.providerConfigurationHttpMessageConverter.write(
-				providerConfiguration, MediaType.APPLICATION_JSON, httpResponse);
+				providerConfiguration.build(), MediaType.APPLICATION_JSON, httpResponse);
 	}
 
 	private static Consumer<List<String>> clientAuthenticationMethods() {

+ 53 - 0
oauth2-authorization-server/src/test/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OidcTests.java

@@ -24,6 +24,7 @@ import java.util.Base64;
 import java.util.HashSet;
 import java.util.List;
 import java.util.Set;
+import java.util.function.Consumer;
 
 import com.nimbusds.jose.jwk.JWKSet;
 import com.nimbusds.jose.jwk.source.JWKSource;
@@ -36,6 +37,7 @@ import org.junit.Test;
 
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
 import org.springframework.context.annotation.Import;
 import org.springframework.http.HttpHeaders;
 import org.springframework.http.HttpStatus;
@@ -69,6 +71,7 @@ import org.springframework.security.oauth2.jwt.NimbusJwtEncoder;
 import org.springframework.security.oauth2.server.authorization.JdbcOAuth2AuthorizationService;
 import org.springframework.security.oauth2.server.authorization.OAuth2Authorization;
 import org.springframework.security.oauth2.server.authorization.OAuth2AuthorizationCode;
+import org.springframework.security.oauth2.server.authorization.OAuth2AuthorizationServerMetadataClaimNames;
 import org.springframework.security.oauth2.server.authorization.OAuth2AuthorizationService;
 import org.springframework.security.oauth2.server.authorization.OAuth2TokenType;
 import org.springframework.security.oauth2.server.authorization.TestOAuth2Authorizations;
@@ -79,6 +82,7 @@ import org.springframework.security.oauth2.server.authorization.client.Registere
 import org.springframework.security.oauth2.server.authorization.client.TestRegisteredClients;
 import org.springframework.security.oauth2.server.authorization.config.annotation.web.configuration.OAuth2AuthorizationServerConfiguration;
 import org.springframework.security.oauth2.server.authorization.jackson2.TestingAuthenticationTokenMixin;
+import org.springframework.security.oauth2.server.authorization.oidc.OidcProviderConfiguration;
 import org.springframework.security.oauth2.server.authorization.settings.AuthorizationServerSettings;
 import org.springframework.security.oauth2.server.authorization.test.SpringTestRule;
 import org.springframework.security.oauth2.server.authorization.token.DelegatingOAuth2TokenGenerator;
@@ -101,6 +105,7 @@ import org.springframework.web.util.UriComponentsBuilder;
 import static org.assertj.core.api.Assertions.assertThat;
 import static org.assertj.core.api.Assertions.assertThatThrownBy;
 import static org.hamcrest.CoreMatchers.containsString;
+import static org.hamcrest.CoreMatchers.hasItems;
 import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.times;
@@ -196,6 +201,17 @@ public class OidcTests {
 				.andExpect(status().is2xxSuccessful());
 	}
 
+	// gh-616
+	@Test
+	public void requestWhenConfigurationRequestAndConfigurationCustomizerSetThenReturnCustomConfigurationResponse() throws Exception {
+		this.spring.register(AuthorizationServerConfigurationWithProviderConfigurationCustomizer.class).autowire();
+
+		this.mvc.perform(get(DEFAULT_OIDC_PROVIDER_CONFIGURATION_ENDPOINT_URI))
+				.andExpect(status().is2xxSuccessful())
+				.andExpect(jsonPath(OAuth2AuthorizationServerMetadataClaimNames.SCOPES_SUPPORTED,
+						hasItems(OidcScopes.OPENID, OidcScopes.PROFILE, OidcScopes.EMAIL)));
+	}
+
 	@Test
 	public void loadContextWhenIssuerNotValidUrlThenThrowException() {
 		assertThatThrownBy(
@@ -464,6 +480,43 @@ public class OidcTests {
 
 	}
 
+	@Configuration
+	@EnableWebSecurity
+	static class AuthorizationServerConfigurationWithProviderConfigurationCustomizer extends AuthorizationServerConfiguration {
+
+		// @formatter:off
+		@Bean
+		public SecurityFilterChain authorizationServerSecurityFilterChain(HttpSecurity http) throws Exception {
+			OAuth2AuthorizationServerConfigurer authorizationServerConfigurer =
+					new OAuth2AuthorizationServerConfigurer();
+			http.apply(authorizationServerConfigurer);
+
+			authorizationServerConfigurer
+					.oidc(oidc ->
+							oidc.providerConfigurationEndpoint(providerConfigurationEndpoint ->
+									providerConfigurationEndpoint
+											.providerConfigurationCustomizer(providerConfigurationCustomizer())));
+
+			RequestMatcher endpointsMatcher = authorizationServerConfigurer.getEndpointsMatcher();
+
+			http
+					.requestMatcher(endpointsMatcher)
+					.authorizeRequests(authorizeRequests ->
+							authorizeRequests.anyRequest().authenticated()
+					)
+					.csrf(csrf -> csrf.ignoringRequestMatchers(endpointsMatcher));
+
+			return http.build();
+		}
+		// @formatter:on
+
+		private Consumer<OidcProviderConfiguration.Builder> providerConfigurationCustomizer() {
+			return (providerConfiguration) ->
+					providerConfiguration.scope(OidcScopes.PROFILE).scope(OidcScopes.EMAIL);
+		}
+
+	}
+
 	@EnableWebSecurity
 	@Import(OAuth2AuthorizationServerConfiguration.class)
 	static class AuthorizationServerConfigurationWithIssuer extends AuthorizationServerConfiguration {

+ 14 - 14
oauth2-authorization-server/src/test/java/org/springframework/security/oauth2/server/authorization/oidc/web/OidcProviderConfigurationEndpointFilterTests.java

@@ -31,6 +31,7 @@ import org.springframework.security.oauth2.server.authorization.settings.Authori
 
 import static org.assertj.core.api.Assertions.assertThat;
 import static org.assertj.core.api.Assertions.assertThatIllegalArgumentException;
+import static org.assertj.core.api.Assertions.assertThatThrownBy;
 import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.verify;
@@ -40,9 +41,11 @@ import static org.mockito.Mockito.verifyNoInteractions;
  * Tests for {@link OidcProviderConfigurationEndpointFilter}.
  *
  * @author Daniel Garnier-Moiroux
+ * @author Joe Grandja
  */
 public class OidcProviderConfigurationEndpointFilterTests {
 	private static final String DEFAULT_OIDC_PROVIDER_CONFIGURATION_ENDPOINT_URI = "/.well-known/openid-configuration";
+	private final OidcProviderConfigurationEndpointFilter filter = new OidcProviderConfigurationEndpointFilter();
 
 	@After
 	public void cleanup() {
@@ -50,35 +53,34 @@ public class OidcProviderConfigurationEndpointFilterTests {
 	}
 
 	@Test
-	public void doFilterWhenNotConfigurationRequestThenNotProcessed() throws Exception {
-		AuthorizationServerSettings authorizationServerSettings = AuthorizationServerSettings.builder().build();
-		AuthorizationServerContextHolder.setContext(new TestAuthorizationServerContext(authorizationServerSettings, null));
-		OidcProviderConfigurationEndpointFilter filter = new OidcProviderConfigurationEndpointFilter();
+	public void setProviderConfigurationCustomizerWhenNullThenThrowIllegalArgumentException() {
+		assertThatThrownBy(() -> this.filter.setProviderConfigurationCustomizer(null))
+				.isInstanceOf(IllegalArgumentException.class)
+				.hasMessage("providerConfigurationCustomizer cannot be null");
+	}
 
+	@Test
+	public void doFilterWhenNotConfigurationRequestThenNotProcessed() throws Exception {
 		String requestUri = "/path";
 		MockHttpServletRequest request = new MockHttpServletRequest("GET", requestUri);
 		request.setServletPath(requestUri);
 		MockHttpServletResponse response = new MockHttpServletResponse();
 		FilterChain filterChain = mock(FilterChain.class);
 
-		filter.doFilter(request, response, filterChain);
+		this.filter.doFilter(request, response, filterChain);
 
 		verify(filterChain).doFilter(any(HttpServletRequest.class), any(HttpServletResponse.class));
 	}
 
 	@Test
 	public void doFilterWhenConfigurationRequestPostThenNotProcessed() throws Exception {
-		AuthorizationServerSettings authorizationServerSettings = AuthorizationServerSettings.builder().build();
-		AuthorizationServerContextHolder.setContext(new TestAuthorizationServerContext(authorizationServerSettings, null));
-		OidcProviderConfigurationEndpointFilter filter = new OidcProviderConfigurationEndpointFilter();
-
 		String requestUri = DEFAULT_OIDC_PROVIDER_CONFIGURATION_ENDPOINT_URI;
 		MockHttpServletRequest request = new MockHttpServletRequest("POST", requestUri);
 		request.setServletPath(requestUri);
 		MockHttpServletResponse response = new MockHttpServletResponse();
 		FilterChain filterChain = mock(FilterChain.class);
 
-		filter.doFilter(request, response, filterChain);
+		this.filter.doFilter(request, response, filterChain);
 
 		verify(filterChain).doFilter(any(HttpServletRequest.class), any(HttpServletResponse.class));
 	}
@@ -103,7 +105,6 @@ public class OidcProviderConfigurationEndpointFilterTests {
 				.tokenIntrospectionEndpoint(tokenIntrospectionEndpoint)
 				.build();
 		AuthorizationServerContextHolder.setContext(new TestAuthorizationServerContext(authorizationServerSettings, null));
-		OidcProviderConfigurationEndpointFilter filter = new OidcProviderConfigurationEndpointFilter();
 
 		String requestUri = DEFAULT_OIDC_PROVIDER_CONFIGURATION_ENDPOINT_URI;
 		MockHttpServletRequest request = new MockHttpServletRequest("GET", requestUri);
@@ -111,7 +112,7 @@ public class OidcProviderConfigurationEndpointFilterTests {
 		MockHttpServletResponse response = new MockHttpServletResponse();
 		FilterChain filterChain = mock(FilterChain.class);
 
-		filter.doFilter(request, response, filterChain);
+		this.filter.doFilter(request, response, filterChain);
 
 		verifyNoInteractions(filterChain);
 
@@ -140,7 +141,6 @@ public class OidcProviderConfigurationEndpointFilterTests {
 				.issuer("https://this is an invalid URL")
 				.build();
 		AuthorizationServerContextHolder.setContext(new TestAuthorizationServerContext(authorizationServerSettings, null));
-		OidcProviderConfigurationEndpointFilter filter = new OidcProviderConfigurationEndpointFilter();
 
 		String requestUri = DEFAULT_OIDC_PROVIDER_CONFIGURATION_ENDPOINT_URI;
 		MockHttpServletRequest request = new MockHttpServletRequest("GET", requestUri);
@@ -149,7 +149,7 @@ public class OidcProviderConfigurationEndpointFilterTests {
 		FilterChain filterChain = mock(FilterChain.class);
 
 		assertThatIllegalArgumentException()
-				.isThrownBy(() -> filter.doFilter(request, response, filterChain))
+				.isThrownBy(() -> this.filter.doFilter(request, response, filterChain))
 				.withMessage("issuer must be a valid URL");
 	}