4545import org .springframework .context .annotation .Bean ;
4646import org .springframework .context .annotation .Configuration ;
4747import org .springframework .context .annotation .Import ;
48+ import org .springframework .context .annotation .Primary ;
4849import org .springframework .http .HttpHeaders ;
4950import org .springframework .jdbc .core .JdbcOperations ;
5051import org .springframework .jdbc .core .JdbcTemplate ;
@@ -158,6 +159,8 @@ public class OAuth2ClientCredentialsGrantTests {
158159
159160 private static AuthenticationFailureHandler authenticationFailureHandler ;
160161
162+ private static PasswordEncoder passwordEncoder ;
163+
161164 public final SpringTestContext spring = new SpringTestContext (this );
162165
163166 @ Autowired
@@ -183,6 +186,9 @@ public static void init() {
183186 authenticationProvidersConsumer = mock (Consumer .class );
184187 authenticationSuccessHandler = mock (AuthenticationSuccessHandler .class );
185188 authenticationFailureHandler = mock (AuthenticationFailureHandler .class );
189+ passwordEncoder = mock (PasswordEncoder .class );
190+ given (passwordEncoder .matches (any (), any ())).willReturn (true );
191+ given (passwordEncoder .upgradeEncoding (any ())).willReturn (false );
186192 db = new EmbeddedDatabaseBuilder ().generateUniqueName (true )
187193 .setType (EmbeddedDatabaseType .HSQL )
188194 .setScriptEncoding ("UTF-8" )
@@ -496,6 +502,26 @@ public void requestWhenTokenRequestWithDPoPProofThenReturnDPoPBoundAccessToken()
496502 .andExpect (jsonPath ("$.token_type" ).value (OAuth2AccessToken .TokenType .DPOP .getValue ()));
497503 }
498504
505+ @ Test
506+ public void requestWhenTokenRequestWithMultiplePasswordEncodersThenPrimaryPasswordEncoderUsed () throws Exception {
507+ this .spring .register (AuthorizationServerConfigurationWithMultiplePasswordEncoders .class ).autowire ();
508+
509+ RegisteredClient registeredClient = TestRegisteredClients .registeredClient2 ().build ();
510+ this .registeredClientRepository .save (registeredClient );
511+
512+ this .mvc
513+ .perform (post (DEFAULT_TOKEN_ENDPOINT_URI )
514+ .param (OAuth2ParameterNames .GRANT_TYPE , AuthorizationGrantType .CLIENT_CREDENTIALS .getValue ())
515+ .param (OAuth2ParameterNames .SCOPE , "scope1 scope2" )
516+ .header (HttpHeaders .AUTHORIZATION ,
517+ "Basic " + encodeBasicAuth (registeredClient .getClientId (), registeredClient .getClientSecret ())))
518+ .andExpect (status ().isOk ())
519+ .andExpect (jsonPath ("$.access_token" ).isNotEmpty ())
520+ .andExpect (jsonPath ("$.scope" ).value ("scope1 scope2" ));
521+
522+ verify (passwordEncoder ).matches (any (), any ());
523+ }
524+
499525 private static String generateDPoPProof (String tokenEndpointUri ) {
500526 // @formatter:off
501527 Map <String , Object > publicJwk = TestJwks .DEFAULT_EC_JWK
@@ -658,4 +684,16 @@ AuthorizationServerSettings authorizationServerSettings() {
658684
659685 }
660686
687+ @ EnableWebSecurity
688+ @ Configuration (proxyBeanMethods = false )
689+ static class AuthorizationServerConfigurationWithMultiplePasswordEncoders extends AuthorizationServerConfiguration {
690+
691+ @ Primary
692+ @ Bean
693+ PasswordEncoder primaryPasswordEncoder () {
694+ return passwordEncoder ;
695+ }
696+
697+ }
698+
661699}
0 commit comments