Search code examples
springspring-bootspring-mvcspring-security

Can't set custom values in server metadata in spring oauth authentication sever


My configuration for server's metadata so far

authorizationServerMetadataEndpoint { authorizationServerMetadataEndpoint ->
                        authorizationServerMetadataEndpoint.authorizationServerMetadataCustomizer { t ->
                            t.apply {
                                authorizationEndpoint(authorizationEndpoint)
                                tokenEndpoint(tokenEndpoint)
                                clientRegistrationEndpoint(registrationEndpoint)
                                issuer(dispatcherServletPath.path)
                                responseType(responseTypeSupported)
                                scopesSupported.forEach { scope -> scope(scope) }
                                tokenIntrospectionEndpoint(introspectionEndpoint)
                                tokenRevocationEndpoint(revocationEndpoint)
                            }.build()
                        }
                    }

but this customization doesn't applies. When calling GET http://localhost:8080/.well-known/oauth-authorization-server, i am getting all the default values not the one I set in the above code. What wrong am i doing.

Here is the complete method

    @Bean
    @Order(Ordered.HIGHEST_PRECEDENCE)
    fun serverSecurityFilterChain(
        http: HttpSecurity,
        authorizationServerSettings: AuthorizationServerSettings, dispatcherServletPath: DispatcherServletPath,
    ): SecurityFilterChain {
        val deviceClientAuthenticationConverter = DeviceClientAuthenticationConverter(
            authorizationServerSettings.deviceAuthorizationEndpoint
        )
        val deviceClientAuthenticationProvider = DeviceClientAuthenticationProvider(registeredClientRepository())

        val authorizationServerConfigurer = OAuth2AuthorizationServerConfigurer()
        return http.csrf { it.disable() }.authorizeHttpRequests {
            it.requestMatchers("/auth/**").permitAll().anyRequest().authenticated()
        }.sessionManagement { it.sessionCreationPolicy(SessionCreationPolicy.STATELESS) }
            .securityMatcher(authorizationServerConfigurer.endpointsMatcher)
            .with(authorizationServerConfigurer) { authorizationServer ->
                authorizationServer

                    .registeredClientRepository(registeredClientRepository())
                    .authorizationService(authorizationService()).deviceAuthorizationEndpoint {
                        it.verificationUri("/activate")
                    }

                    .deviceVerificationEndpoint { it.consentPage(CONSENT_PAGE_URI) }


                    .clientAuthentication { clientAuthentication ->
                        clientAuthentication.authenticationConverter(deviceClientAuthenticationConverter)
                            .authenticationProvider(deviceClientAuthenticationProvider)
                    }

                    .authorizationEndpoint { authorizationEndpoint ->
                        authorizationEndpoint.consentPage(CONSENT_PAGE_URI)
                    }

                    .authorizationServerMetadataEndpoint { authorizationServerMetadataEndpoint ->
                        authorizationServerMetadataEndpoint.authorizationServerMetadataCustomizer { t ->
                            t.apply {
                                authorizationEndpoint(authorizationEndpoint)
                                tokenEndpoint(tokenEndpoint)
                                clientRegistrationEndpoint(registrationEndpoint)
                                issuer(dispatcherServletPath.path)
                                responseType(responseTypeSupported)
                                scopesSupported.forEach { scope -> scope(scope) }
                                tokenIntrospectionEndpoint(introspectionEndpoint)
                                tokenRevocationEndpoint(revocationEndpoint)
                            }.build()
                        }
                    }.tokenEndpoint {
                        it.authenticationProvider(authManager())
                    }.tokenRevocationEndpoint {}.tokenIntrospectionEndpoint {}

                    .oidc {
                        it.logoutEndpoint { }.userInfoEndpoint { }.clientRegistrationEndpoint { }
                            .providerConfigurationEndpoint { }
                    }
            }.exceptionHandling { exceptions ->
                exceptions.defaultAuthenticationEntryPointFor(
                    LoginUrlAuthenticationEntryPoint("/auth/login"), MediaTypeRequestMatcher(MediaType.TEXT_HTML)
                )
            }.addFilterBefore(jwtAuthorizationFilter, UsernamePasswordAuthenticationFilter::class.java).build()
    }

response is

{
  "issuer": "http://localhost:8080",
  "authorization_endpoint": "http://localhost:8080/oauth2/authorize",
  "device_authorization_endpoint": "http://localhost:8080/oauth2/device_authorization",
  "token_endpoint": "http://localhost:8080/oauth2/token",
  "token_endpoint_auth_methods_supported": [
    "client_secret_basic",
    "client_secret_post",
    "client_secret_jwt",
    "private_key_jwt",
    "tls_client_auth",
    "self_signed_tls_client_auth"
  ],
  "jwks_uri": "http://localhost:8080/oauth2/jwks",
  "response_types_supported": [
    "code"
  ],
  "grant_types_supported": [
    "authorization_code",
    "client_credentials",
    "refresh_token",
    "urn:ietf:params:oauth:grant-type:device_code",
    "urn:ietf:params:oauth:grant-type:token-exchange"
  ],
  "revocation_endpoint": "http://localhost:8080/oauth2/revoke",
  "revocation_endpoint_auth_methods_supported": [
    "client_secret_basic",
    "client_secret_post",
    "client_secret_jwt",
    "private_key_jwt",
    "tls_client_auth",
    "self_signed_tls_client_auth"
  ],
  "introspection_endpoint": "http://localhost:8080/oauth2/introspect",
  "introspection_endpoint_auth_methods_supported": [
    "client_secret_basic",
    "client_secret_post",
    "client_secret_jwt",
    "private_key_jwt",
    "tls_client_auth",
    "self_signed_tls_client_auth"
  ],
  "code_challenge_methods_supported": [
    "S256"
  ],
  "tls_client_certificate_bound_access_tokens": true
}

which is different from what I wanted. Also how to change the url of metadata?


Solution

  • Custom .well-known/openid-configuration metadata need provide providerConfigurationCustomizer like so

     oidc {
             c -> c.providerConfigurationEndpoint { p -> p.providerConfigurationCustomizer{
                            it.issuer(serverMetadata.issuer)
                                .authorizationEndpoint(serverMetadata.authorizationEndpoint)
                                .tokenEndpoint(serverMetadata.tokenEndpoint)
                                .jwkSetUrl(serverMetadata.jwksUri)
                                .tokenRevocationEndpoint(serverMetadata.revocationEndpoint)
                                .clientRegistrationEndpoint(serverMetadata.registrationEndpoint)
                                .tokenRevocationEndpoint(serverMetadata.revocationEndpoint)
                            }  }
                        }