Skip to content

Commit 4cfe59c

Browse files
committed
Path component for issuer identifier should be disabled by default
Issue gh-1342 Closes gh-1611
1 parent 6eda8c6 commit 4cfe59c

File tree

35 files changed

+365
-107
lines changed

35 files changed

+365
-107
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
/*
2+
* Copyright 2020-2024 the original author or authors.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* https://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
package sample.multitenancy;
17+
18+
import org.springframework.context.annotation.Bean;
19+
import org.springframework.context.annotation.Configuration;
20+
import org.springframework.security.oauth2.server.authorization.settings.AuthorizationServerSettings;
21+
22+
@Configuration(proxyBeanMethods = false)
23+
public class AuthorizationServerSettingsConfig {
24+
25+
@Bean
26+
AuthorizationServerSettings authorizationServerSettings() {
27+
return AuthorizationServerSettings.builder().multipleIssuersAllowed(true).build();
28+
}
29+
30+
}

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2AuthorizationEndpointConfigurer.java

+8-5
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@
5151
import org.springframework.util.Assert;
5252
import org.springframework.util.StringUtils;
5353

54-
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuerPattern;
54+
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuersPattern;
5555

5656
/**
5757
* Configurer for the OAuth 2.0 Authorization Endpoint.
@@ -211,7 +211,9 @@ void setSessionAuthenticationStrategy(SessionAuthenticationStrategy sessionAuthe
211211
@Override
212212
void init(HttpSecurity httpSecurity) {
213213
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(httpSecurity);
214-
String authorizationEndpointUri = withMultipleIssuerPattern(authorizationServerSettings.getAuthorizationEndpoint());
214+
String authorizationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
215+
withMultipleIssuersPattern(authorizationServerSettings.getAuthorizationEndpoint()) :
216+
authorizationServerSettings.getAuthorizationEndpoint();
215217
this.requestMatcher = new OrRequestMatcher(
216218
new AntPathRequestMatcher(authorizationEndpointUri, HttpMethod.GET.name()),
217219
new AntPathRequestMatcher(authorizationEndpointUri, HttpMethod.POST.name()));
@@ -229,11 +231,12 @@ void init(HttpSecurity httpSecurity) {
229231
void configure(HttpSecurity httpSecurity) {
230232
AuthenticationManager authenticationManager = httpSecurity.getSharedObject(AuthenticationManager.class);
231233
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(httpSecurity);
234+
String authorizationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
235+
withMultipleIssuersPattern(authorizationServerSettings.getAuthorizationEndpoint()) :
236+
authorizationServerSettings.getAuthorizationEndpoint();
232237

233238
OAuth2AuthorizationEndpointFilter authorizationEndpointFilter =
234-
new OAuth2AuthorizationEndpointFilter(
235-
authenticationManager,
236-
withMultipleIssuerPattern(authorizationServerSettings.getAuthorizationEndpoint()));
239+
new OAuth2AuthorizationEndpointFilter(authenticationManager, authorizationEndpointUri);
237240
List<AuthenticationConverter> authenticationConverters = createDefaultAuthenticationConverters();
238241
if (!this.authorizationRequestConverters.isEmpty()) {
239242
authenticationConverters.addAll(0, this.authorizationRequestConverters);

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2AuthorizationServerConfigurer.java

+10-5
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
import org.springframework.security.web.util.matcher.RequestMatcher;
5757
import org.springframework.util.Assert;
5858

59-
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuerPattern;
59+
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuersPattern;
6060

6161
/**
6262
* An {@link AbstractHttpConfigurer} for OAuth 2.0 Authorization Server support.
@@ -315,8 +315,10 @@ public void init(HttpSecurity httpSecurity) {
315315
configurer.init(httpSecurity);
316316
requestMatchers.add(configurer.getRequestMatcher());
317317
});
318-
requestMatchers.add(new AntPathRequestMatcher(
319-
withMultipleIssuerPattern(authorizationServerSettings.getJwkSetEndpoint()), HttpMethod.GET.name()));
318+
String jwkSetEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
319+
withMultipleIssuersPattern(authorizationServerSettings.getJwkSetEndpoint()) :
320+
authorizationServerSettings.getJwkSetEndpoint();
321+
requestMatchers.add(new AntPathRequestMatcher(jwkSetEndpointUri, HttpMethod.GET.name()));
320322
this.endpointsMatcher = new OrRequestMatcher(requestMatchers);
321323

322324
ExceptionHandlingConfigurer<HttpSecurity> exceptionHandling = httpSecurity.getConfigurer(ExceptionHandlingConfigurer.class);
@@ -343,8 +345,11 @@ public void configure(HttpSecurity httpSecurity) {
343345

344346
JWKSource<com.nimbusds.jose.proc.SecurityContext> jwkSource = OAuth2ConfigurerUtils.getJwkSource(httpSecurity);
345347
if (jwkSource != null) {
346-
NimbusJwkSetEndpointFilter jwkSetEndpointFilter = new NimbusJwkSetEndpointFilter(
347-
jwkSource, withMultipleIssuerPattern(authorizationServerSettings.getJwkSetEndpoint()));
348+
String jwkSetEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
349+
withMultipleIssuersPattern(authorizationServerSettings.getJwkSetEndpoint()) :
350+
authorizationServerSettings.getJwkSetEndpoint();
351+
NimbusJwkSetEndpointFilter jwkSetEndpointFilter =
352+
new NimbusJwkSetEndpointFilter(jwkSource, jwkSetEndpointUri);
348353
httpSecurity.addFilterBefore(postProcess(jwkSetEndpointFilter), AbstractPreAuthenticatedProcessingFilter.class);
349354
}
350355
}

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2AuthorizationServerMetadataEndpointConfigurer.java

+6-2
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
import org.springframework.security.config.annotation.ObjectPostProcessor;
2222
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
2323
import org.springframework.security.oauth2.server.authorization.OAuth2AuthorizationServerMetadata;
24+
import org.springframework.security.oauth2.server.authorization.settings.AuthorizationServerSettings;
2425
import org.springframework.security.oauth2.server.authorization.web.OAuth2AuthorizationServerMetadataEndpointFilter;
2526
import org.springframework.security.web.authentication.preauth.AbstractPreAuthenticatedProcessingFilter;
2627
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
@@ -69,8 +70,11 @@ void addDefaultAuthorizationServerMetadataCustomizer(
6970

7071
@Override
7172
void init(HttpSecurity httpSecurity) {
72-
this.requestMatcher = new AntPathRequestMatcher(
73-
"/.well-known/oauth-authorization-server/**", HttpMethod.GET.name());
73+
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(httpSecurity);
74+
String authorizationServerMetadataEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
75+
"/.well-known/oauth-authorization-server/**" :
76+
"/.well-known/oauth-authorization-server";
77+
this.requestMatcher = new AntPathRequestMatcher(authorizationServerMetadataEndpointUri, HttpMethod.GET.name());
7478
}
7579

7680
@Override

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2ClientAuthenticationConfigurer.java

+17-13
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@
5353
import org.springframework.security.web.util.matcher.RequestMatcher;
5454
import org.springframework.util.Assert;
5555

56-
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuerPattern;
56+
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuersPattern;
5757

5858
/**
5959
* Configurer for OAuth 2.0 Client Authentication.
@@ -163,19 +163,23 @@ public OAuth2ClientAuthenticationConfigurer errorResponseHandler(AuthenticationF
163163
@Override
164164
void init(HttpSecurity httpSecurity) {
165165
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(httpSecurity);
166+
String tokenEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
167+
withMultipleIssuersPattern(authorizationServerSettings.getTokenEndpoint()) :
168+
authorizationServerSettings.getTokenEndpoint();
169+
String tokenIntrospectionEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
170+
withMultipleIssuersPattern(authorizationServerSettings.getTokenIntrospectionEndpoint()) :
171+
authorizationServerSettings.getTokenIntrospectionEndpoint();
172+
String tokenRevocationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
173+
withMultipleIssuersPattern(authorizationServerSettings.getTokenRevocationEndpoint()) :
174+
authorizationServerSettings.getTokenRevocationEndpoint();
175+
String deviceAuthorizationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
176+
withMultipleIssuersPattern(authorizationServerSettings.getDeviceAuthorizationEndpoint()) :
177+
authorizationServerSettings.getDeviceAuthorizationEndpoint();
166178
this.requestMatcher = new OrRequestMatcher(
167-
new AntPathRequestMatcher(
168-
withMultipleIssuerPattern(authorizationServerSettings.getTokenEndpoint()),
169-
HttpMethod.POST.name()),
170-
new AntPathRequestMatcher(
171-
withMultipleIssuerPattern(authorizationServerSettings.getTokenIntrospectionEndpoint()),
172-
HttpMethod.POST.name()),
173-
new AntPathRequestMatcher(
174-
withMultipleIssuerPattern(authorizationServerSettings.getTokenRevocationEndpoint()),
175-
HttpMethod.POST.name()),
176-
new AntPathRequestMatcher(
177-
withMultipleIssuerPattern(authorizationServerSettings.getDeviceAuthorizationEndpoint()),
178-
HttpMethod.POST.name()));
179+
new AntPathRequestMatcher(tokenEndpointUri, HttpMethod.POST.name()),
180+
new AntPathRequestMatcher(tokenIntrospectionEndpointUri, HttpMethod.POST.name()),
181+
new AntPathRequestMatcher(tokenRevocationEndpointUri, HttpMethod.POST.name()),
182+
new AntPathRequestMatcher(deviceAuthorizationEndpointUri, HttpMethod.POST.name()));
179183

180184
List<AuthenticationProvider> authenticationProviders = createDefaultAuthenticationProviders(httpSecurity);
181185
if (!this.authenticationProviders.isEmpty()) {

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2ConfigurerUtils.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ final class OAuth2ConfigurerUtils {
5757
private OAuth2ConfigurerUtils() {
5858
}
5959

60-
static String withMultipleIssuerPattern(String endpointUri) {
60+
static String withMultipleIssuersPattern(String endpointUri) {
6161
Assert.hasText(endpointUri, "endpointUri cannot be empty");
6262
return endpointUri.startsWith("/") ?
6363
"/**" + endpointUri :

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2DeviceAuthorizationEndpointConfigurer.java

+9-5
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@
4545
import org.springframework.util.Assert;
4646
import org.springframework.util.StringUtils;
4747

48-
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuerPattern;
48+
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuersPattern;
4949

5050
/**
5151
* Configurer for the OAuth 2.0 Device Authorization Endpoint.
@@ -167,8 +167,10 @@ public OAuth2DeviceAuthorizationEndpointConfigurer verificationUri(String verifi
167167
public void init(HttpSecurity builder) {
168168
AuthorizationServerSettings authorizationServerSettings =
169169
OAuth2ConfigurerUtils.getAuthorizationServerSettings(builder);
170-
this.requestMatcher = new AntPathRequestMatcher(
171-
withMultipleIssuerPattern(authorizationServerSettings.getDeviceAuthorizationEndpoint()), HttpMethod.POST.name());
170+
String deviceAuthorizationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
171+
withMultipleIssuersPattern(authorizationServerSettings.getDeviceAuthorizationEndpoint()) :
172+
authorizationServerSettings.getDeviceAuthorizationEndpoint();
173+
this.requestMatcher = new AntPathRequestMatcher(deviceAuthorizationEndpointUri, HttpMethod.POST.name());
172174

173175
List<AuthenticationProvider> authenticationProviders = createDefaultAuthenticationProviders(builder);
174176
if (!this.authenticationProviders.isEmpty()) {
@@ -184,9 +186,11 @@ public void configure(HttpSecurity builder) {
184186
AuthenticationManager authenticationManager = builder.getSharedObject(AuthenticationManager.class);
185187
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(builder);
186188

189+
String deviceAuthorizationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
190+
withMultipleIssuersPattern(authorizationServerSettings.getDeviceAuthorizationEndpoint()) :
191+
authorizationServerSettings.getDeviceAuthorizationEndpoint();
187192
OAuth2DeviceAuthorizationEndpointFilter deviceAuthorizationEndpointFilter =
188-
new OAuth2DeviceAuthorizationEndpointFilter(
189-
authenticationManager, withMultipleIssuerPattern(authorizationServerSettings.getDeviceAuthorizationEndpoint()));
193+
new OAuth2DeviceAuthorizationEndpointFilter(authenticationManager, deviceAuthorizationEndpointUri);
190194

191195
List<AuthenticationConverter> authenticationConverters = createDefaultAuthenticationConverters();
192196
if (!this.deviceAuthorizationRequestConverters.isEmpty()) {

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2DeviceVerificationEndpointConfigurer.java

+8-5
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,7 @@
5050
import org.springframework.util.Assert;
5151
import org.springframework.util.StringUtils;
5252

53-
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuerPattern;
53+
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuersPattern;
5454

5555
/**
5656
* Configurer for the OAuth 2.0 Device Verification Endpoint.
@@ -197,7 +197,9 @@ public OAuth2DeviceVerificationEndpointConfigurer consentPage(String consentPage
197197
public void init(HttpSecurity builder) {
198198
AuthorizationServerSettings authorizationServerSettings =
199199
OAuth2ConfigurerUtils.getAuthorizationServerSettings(builder);
200-
String deviceVerificationEndpointUri = withMultipleIssuerPattern(authorizationServerSettings.getDeviceVerificationEndpoint());
200+
String deviceVerificationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
201+
withMultipleIssuersPattern(authorizationServerSettings.getDeviceVerificationEndpoint()) :
202+
authorizationServerSettings.getDeviceVerificationEndpoint();
201203
this.requestMatcher = new OrRequestMatcher(
202204
new AntPathRequestMatcher(deviceVerificationEndpointUri, HttpMethod.GET.name()),
203205
new AntPathRequestMatcher(deviceVerificationEndpointUri, HttpMethod.POST.name()));
@@ -217,10 +219,11 @@ public void configure(HttpSecurity builder) {
217219
AuthorizationServerSettings authorizationServerSettings =
218220
OAuth2ConfigurerUtils.getAuthorizationServerSettings(builder);
219221

222+
String deviceVerificationEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
223+
withMultipleIssuersPattern(authorizationServerSettings.getDeviceVerificationEndpoint()) :
224+
authorizationServerSettings.getDeviceVerificationEndpoint();
220225
OAuth2DeviceVerificationEndpointFilter deviceVerificationEndpointFilter =
221-
new OAuth2DeviceVerificationEndpointFilter(
222-
authenticationManager,
223-
withMultipleIssuerPattern(authorizationServerSettings.getDeviceVerificationEndpoint()));
226+
new OAuth2DeviceVerificationEndpointFilter(authenticationManager, deviceVerificationEndpointUri);
224227
List<AuthenticationConverter> authenticationConverters = createDefaultAuthenticationConverters();
225228
if (!this.deviceVerificationRequestConverters.isEmpty()) {
226229
authenticationConverters.addAll(0, this.deviceVerificationRequestConverters);

Diff for: oauth2-authorization-server/src/main/java/org/springframework/security/oauth2/server/authorization/config/annotation/web/configurers/OAuth2TokenEndpointConfigurer.java

+9-6
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
import org.springframework.security.web.util.matcher.RequestMatcher;
5757
import org.springframework.util.Assert;
5858

59-
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuerPattern;
59+
import static org.springframework.security.oauth2.server.authorization.config.annotation.web.configurers.OAuth2ConfigurerUtils.withMultipleIssuersPattern;
6060

6161
/**
6262
* Configurer for the OAuth 2.0 Token Endpoint.
@@ -166,8 +166,10 @@ public OAuth2TokenEndpointConfigurer errorResponseHandler(AuthenticationFailureH
166166
@Override
167167
void init(HttpSecurity httpSecurity) {
168168
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(httpSecurity);
169-
this.requestMatcher = new AntPathRequestMatcher(
170-
withMultipleIssuerPattern(authorizationServerSettings.getTokenEndpoint()), HttpMethod.POST.name());
169+
String tokenEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
170+
withMultipleIssuersPattern(authorizationServerSettings.getTokenEndpoint()) :
171+
authorizationServerSettings.getTokenEndpoint();
172+
this.requestMatcher = new AntPathRequestMatcher(tokenEndpointUri, HttpMethod.POST.name());
171173

172174
List<AuthenticationProvider> authenticationProviders = createDefaultAuthenticationProviders(httpSecurity);
173175
if (!this.authenticationProviders.isEmpty()) {
@@ -183,10 +185,11 @@ void configure(HttpSecurity httpSecurity) {
183185
AuthenticationManager authenticationManager = httpSecurity.getSharedObject(AuthenticationManager.class);
184186
AuthorizationServerSettings authorizationServerSettings = OAuth2ConfigurerUtils.getAuthorizationServerSettings(httpSecurity);
185187

188+
String tokenEndpointUri = authorizationServerSettings.isMultipleIssuersAllowed() ?
189+
withMultipleIssuersPattern(authorizationServerSettings.getTokenEndpoint()) :
190+
authorizationServerSettings.getTokenEndpoint();
186191
OAuth2TokenEndpointFilter tokenEndpointFilter =
187-
new OAuth2TokenEndpointFilter(
188-
authenticationManager,
189-
withMultipleIssuerPattern(authorizationServerSettings.getTokenEndpoint()));
192+
new OAuth2TokenEndpointFilter(authenticationManager, tokenEndpointUri);
190193
List<AuthenticationConverter> authenticationConverters = createDefaultAuthenticationConverters();
191194
if (!this.accessTokenRequestConverters.isEmpty()) {
192195
authenticationConverters.addAll(0, this.accessTokenRequestConverters);

0 commit comments

Comments
 (0)