OAuth2注销在使用Spring Webflux的Spring Security中不起作用

yk9xbfzb  于 2023-06-22  发布在  Spring
关注(0)|答案(1)|浏览(132)

我有一个使用Spring Security的Sping Boot Webflux应用程序。它使用OAuth2进行身份验证。Login工作正常。但是logout不起作用。我可以转到/logout页面并单击Logout按钮,它会再次将我带回Login页面,这很好,但当我返回需要身份验证的页面时,它会自动将我重新登录,而不会提示我再次登录。
这是我的代码。

@Configuration
@EnableWebFluxSecurity
@EnableReactiveMethodSecurity
public class OAuth2SecurityConfiguration {

    private final AuthenticationProperties authenticationProperties;

    @Autowired
    public OAuth2SecurityConfiguration(AuthenticationProperties authenticationProperties) {
        this.authenticationProperties = authenticationProperties;
    }

    @Bean
    public SecurityWebFilterChain securityWebFilterChain(ServerHttpSecurity http) {
        return http
            .authorizeExchange(authorizeExchangeSpec -> {
                authorizeExchangeSpec.pathMatchers(HttpMethod.OPTIONS).permitAll();
                authorizeExchangeSpec.pathMatchers(HttpMethod.GET, "/assets/**").permitAll();
                authorizeExchangeSpec.anyExchange().authenticated();
            })
            .oauth2Login(withDefaults())
            .logout(logoutSpec -> logoutSpec.logoutSuccessHandler(oidcLogoutSuccessHandler()))
            .build();
    }

    public OidcClientInitiatedServerLogoutSuccessHandler oidcLogoutSuccessHandler() {
        var successHandler = new OidcClientInitiatedServerLogoutSuccessHandler(this.clientRegistrationRepository());
        successHandler.setPostLogoutRedirectUri("{baseUrl}");

        return successHandler;
    }

    @Bean
    public ReactiveClientRegistrationRepository clientRegistrationRepository() {
        return new InMemoryReactiveClientRegistrationRepository(this.oktaClientRegistration());
    }

    private ClientRegistration oktaClientRegistration() {
        return ClientRegistration
            .withRegistrationId("okta")
            .clientId(authenticationProperties.getOauth2().getClient("okta").getClientId())
            .clientSecret(authenticationProperties.getOauth2().getClient("okta").getClientSecret())
            .redirectUri("{baseUrl}/login/oauth2/code/{registrationId}")
            .scope(authenticationProperties.getOauth2().getClient("okta").getScope())
            .authorizationGrantType(new AuthorizationGrantType("authorization_code"))
            .authorizationUri(authenticationProperties.getOauth2().getClient("okta").getAuthorizationUri())
            .tokenUri(authenticationProperties.getOauth2().getClient("okta").getTokenUri())
            .userInfoUri(authenticationProperties.getOauth2().getClient("okta").getUserInfoUri())
            .jwkSetUri(authenticationProperties.getOauth2().getClient("okta").getJwkSetUri())
            .userNameAttributeName("email")
            .clientName("okta")
            .build();
    }
}

有什么办法能解决这个问题吗。

jyztefdp

jyztefdp1#

好的,我能够解决这个问题,看起来像是当您手动配置ClientRegistrationend_session_endpoint没有设置,因为RP发起的注销不起作用。解决方法是这样设置变量。

private ClientRegistration oktaClientRegistration() {
    return CommonOAuth2Provider.OKTA
        .getBuilder("okta")
        .clientId(authenticationProperties.getOauth2().getClient("okta").getClientId())
        .clientSecret(authenticationProperties.getOauth2().getClient("okta").getClientSecret())
        .authorizationUri(authenticationProperties.getOauth2().getClient("okta").getAuthorizationUri())
        .redirectUri("{baseUrl}/login/oauth2/code/{registrationId}")
        .scope(authenticationProperties.getOauth2().getClient("okta").getScope())
        .tokenUri(authenticationProperties.getOauth2().getClient("okta").getTokenUri())
        .userInfoUri(authenticationProperties.getOauth2().getClient("okta").getUserInfoUri())
        .jwkSetUri(authenticationProperties.getOauth2().getClient("okta").getJwkSetUri())
        .userNameAttributeName(IdTokenClaimNames.SUB)
        .clientName("Okta")
        .providerConfigurationMetadata(Map.of("end_session_endpoint", "OKTADOMAIN/oauth2/default/v1/logout"))
        .build();

Okta就是这种情况,其他OAuth提供商可能需要不同的解决方案。

相关问题