Describe the bug An error occurs when the application integrated Spring Gateway and Spring Security OAuth2 Client goes through the OAuth login process.
java.lang.IllegalStateException: No provider found for class org.springframework.security.oauth2.client.authentication.OAuth2AuthorizationCodeAuthenticationToken
at org.springframework.security.web.server.authentication.AuthenticationWebFilter.lambda$authenticate$6(AuthenticationWebFilter.java:124) ~[spring-security-web-6.2.8.jar:6.2.8]
Suppressed: reactor.core.publisher.FluxOnAssembly$OnAssemblyException:
Error has been observed at the following site(s):
*__checkpoint ⇢ OAuth2LoginAuthenticationWebFilter [DefaultWebFilterChain]
*__checkpoint ⇢ OAuth2AuthorizationRequestRedirectWebFilter [DefaultWebFilterChain]
*__checkpoint ⇢ ReactorContextWebFilter [DefaultWebFilterChain]
*__checkpoint ⇢ HttpHeaderWriterWebFilter [DefaultWebFilterChain]
*__checkpoint ⇢ ServerWebExchangeReactorContextWebFilter [DefaultWebFilterChain]
*__checkpoint ⇢ org.springframework.security.web.server.WebFilterChainProxy [DefaultWebFilterChain]
*__checkpoint ⇢ HTTP GET "/login/oauth2/code/capyId?code=LgletqbOVmz4Ae8ZBiseGO8rLQzxbfB__e7qloE7zc-TvH2WaFRqrOdqt8--p4E6JhglkkVjkfXFrOlrEuP-KYqFlohaJMOFijf-hEFRuDNUY3ne5NFIiEk0mEXJydVO&state=RZi5-LwSqzw6Yi_Um0c0zZj9HEHQq0Rjwhr6wc9XNZk%3D" [ExceptionHandlingWebHandler]
Original Stack Trace:
at org.springframework.security.web.server.authentication.AuthenticationWebFilter.lambda$authenticate$6(AuthenticationWebFilter.java:124) ~[spring-security-web-6.2.8.jar:6.2.8]
at reactor.core.publisher.MonoDefer.subscribe(MonoDefer.java:45) ~[reactor-core-3.6.12.jar:3.6.12]
at reactor.core.publisher.Mono.subscribe(Mono.java:4576) ~[reactor-core-3.6.12.jar:3.6.12]
To Reproduce
There are two applications in my project. The first app is authorization-server, integrated spring-security-oauth2-authorization-server. (authorization server has enabled OAuth2 and OIDC.)
The second is BFF(Backends For Frontends) app , integrated spring-cloud-gateway and spring-boot-starter-oauth2-client. (this app has enabled oauth2login)
The OAuth2 login process can succeed only when the second application’s scope is configured as openid. If the scope is set to profile or myscope, the error will occur.
The error occurred in this URL request.
/login/oauth2/code/capyId?code=LgletqbOVmz4Ae8ZBiseGO8rLQzxbfB__e7qloE7zc-TvH2WaFRqrOdqt8--p4E6JhglkkVjkfXFrOlrEuP-KYqFlohaJMOFijf-hEFRuDNUY3ne5NFIiEk0mEXJydVO&state=RZi5-LwSqzw6Yi_Um0c0zZj9HEHQq0Rjwhr6wc9XNZk%3D
Expected behavior
I hope to successfully complete the OAuth2 login process without configuring the openid scope.
Sample
The authorization-server code:
public class AuthSecurityConfig {
@Bean
@Order(Ordered.HIGHEST_PRECEDENCE)
public SecurityFilterChain oAuth2authorizationServerSecurityFilterChain(HttpSecurity http) throws Exception {
OAuth2AuthorizationServerConfiguration.applyDefaultSecurity(http);
OAuth2AuthorizationServerConfigurer authorizationServerConfigurer = http.getConfigurer(OAuth2AuthorizationServerConfigurer.class);
authorizationServerConfigurer.authorizationService(authorizationService())
.oidc(withDefaults())
;
return http
.formLogin(withDefaults())
.build();
}
@Bean
public RegisteredClientRepository clientRepository(){
RegisteredClient client = RegisteredClient.withId("capyId").clientId("capyId").clientSecret("{noop}capySecret")
.clientAuthenticationMethod(ClientAuthenticationMethod.CLIENT_SECRET_BASIC)
.authorizationGrantType(AuthorizationGrantType.AUTHORIZATION_CODE)
.authorizationGrantType(AuthorizationGrantType.REFRESH_TOKEN)
.authorizationGrantType(AuthorizationGrantType.CLIENT_CREDENTIALS)
.tokenSettings(TokenSettings.builder().accessTokenTimeToLive(Duration.ofSeconds(1800)).build())
.clientSettings(ClientSettings.builder().requireAuthorizationConsent(false).build())
.redirectUri("http://192.168.1.1:8080/login/oauth2/code/capyId")
.scope(OidcScopes.PROFILE)
.scope(OidcScopes.OPENID)
.scope("myscope")
.build();
InMemoryRegisteredClientRepository repository = new InMemoryRegisteredClientRepository(client);
return repository;
}
}
The BFF app code:
@Configuration
@EnableWebFluxSecurity
public class OAuth2LoginSecurityConfig {
@Bean
public SecurityWebFilterChain securityFilterChain(ServerHttpSecurity http) {
return http
.oauth2Login(Customizer.withDefaults())
.csrf(ServerHttpSecurity.CsrfSpec::disable)
.build();
}
@Bean
public JwtDecoder jwtDecoder(RSAPublicKey rsaPublicKey) {
return NimbusJwtDecoder.withPublicKey(rsaPublicKey).build();
}
}
The error occurred in this application.yaml
spring:
security:
oauth2:
client:
registration:
capyId:
provider: capyjara
client-id: capyId
client-secret: capySecret
client-authentication-method: client_secret_basic
authorization-grant-type: authorization_code
redirect-uri: http://192.168.1.1:8080/login/oauth2/code/{registrationId}
scope: profile
client-name: Capyjara
provider:
capyjara:
authorization-uri: http://192.168.1.1:8080/auth/oauth2/authorize
token-uri: http://192.168.1.1:8080/auth/oauth2/token
jwk-set-uri: http://192.168.1.1:8080/auth/oauth2/jwks
user-info-uri: http://192.168.1.1:8080/auth/userinfo
user-name-attribute: sub
oauth2login succeed in this application.yaml
spring:
security:
oauth2:
client:
registration:
capyId:
provider: capyjara
client-id: capyId
client-secret: capySecret
client-authentication-method: client_secret_basic
authorization-grant-type: authorization_code
redirect-uri: http://192.168.1.1:8080/login/oauth2/code/{registrationId}
scope: openid
client-name: Capyjara
provider:
capyjara:
authorization-uri: http://192.168.1.1:8080/auth/oauth2/authorize
token-uri: http://192.168.1.1:8080/auth/oauth2/token
jwk-set-uri: http://192.168.1.1:8080/auth/oauth2/jwks
user-info-uri: http://192.168.1.1:8080/auth/userinfo
user-name-attribute: sub
Comment From: SherryXRJ
I have visited spring-cloud-gateway-issue-1534 and spring-security-issue-12615, but the issue cannot be resolved.
I don’t know why the openid scope is required for the OAuth2 login process.
Comment From: sjohnr
@SherryXRJ, thanks for getting in touch, but it feels like this is a question that would be better suited to Stack Overflow. We prefer to use GitHub issues only for bugs and enhancements. Feel free to update this issue with a link to the re-posted question (so that other people can find it) or add a minimal sample that reproduces this issue if you feel this is a genuine bug.
Having said that,
I don’t know why the openid scope is required for the OAuth2 login process.
the openid scope is required to use OIDC to login per the OpenID Connect 1.0 Core specification. See Authentication Request regarding the scope parameter, which specifies that openid is required.