java - 为什么 Spring SAML 阻止 Spring OAuth2 工作?

标签 java spring spring-security spring-security-oauth2 spring-saml

我正在将 Spring SAML 添加到一些迄今为止仅使用 OAuth2 的软件中。我需要确保 OAuth 仍然有效,因为 SAML 仅适用于我们的部分客户。

我遇到了一个问题,旧的 oAuth 似乎不再起作用(尽管 SAML 基本上没问题)。似乎身份验证管理器正在以某种方式被覆盖,但尚不清楚如何或为何。这是我的 WebSecurityConfig.java 中的相关代码:

@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
    auth.userDetailsService(userDetailsService)
            .passwordEncoder(passwordService.getEncoder())
            .and()
            .authenticationProvider(samlAuthenticationProvider)
            .authenticationProvider(oAuth2AuthenticationProvider());
}

和 SAMLConfig.java:

@Bean
public SAMLProcessingFilter samlWebSSOProcessingFilter() throws Exception {
    SAMLProcessingFilter samlWebSSOProcessingFilter = new SAMLProcessingFilter();
    samlWebSSOProcessingFilter.setAuthenticationManager(authenticationManager());
    samlWebSSOProcessingFilter.setAuthenticationSuccessHandler(successRedirectHandler());
    samlWebSSOProcessingFilter.setAuthenticationFailureHandler(authenticationFailureHandler());
    return samlWebSSOProcessingFilter;
}

@Bean
public AuthenticationManager authenticationManager() {
    return new ProviderManager(Collections.singletonList(samlAuthenticationProvider()));
}

显然,这是错误的,但目前还不清楚如何纠正它。

当我调试时,AuthenticationManagerBuilder.performBuild() 在启动时被调用三次。

  • 第一次使用 SAML、OAuth2 和 Dao AuthenticationProvider 构建一个。
  • 第二个使用 AnonymousAuthenticationProvider 构建一个。
  • 第三个与另一个 DaoAuthenticationProvider 构建一个。

登录时,ProviderManager.authenticate() 被调用两次。

  • 第一次,它只有一个提供程序,即 AnonymousAuthenticationProvider。这不会进行身份验证。
  • 第二次是家长经理到第一次。它只有一个提供程序,即 SAMLAuthenticationProvider。如果在 SAML 中找不到我要进行身份验证的用户,这仍然是最后一个被调用的提供者或管理器。
为什么?如何更正此问题,以便在某些情况下将凭据定向到 SAML,在所有其他情况下将凭据定向到 OAuth,或者允许任何在 SAML 中不起作用的凭据溢出到 OAuth?

最佳答案

new ProviderManager()创建一个跳过构建器进程的 AuthenticationManager,这就是为什么它在调试时不显示 performBuild() .

authenticationManager() bean 方法旨在返回现有的全局 AuthenticationManager,但问题使用它的方式却返回一个新的不同的 AuthenticationManager,覆盖构建器返回的内容。这就是为什么它在调试时确实出现 authenticate() ,而内置的 AuthenticationManager 则没有。

解决方案是将现有的 AuthenticationManager 传递给SAMLProcessingFilter.setAuthenticationManager() ,而不是一个新的。我这样做的方法是将所有代码从 SAMLConfig.java 移动到 WebSecurityConfig.java,这更简单,但这不是唯一的方法。

关于java - 为什么 Spring SAML 阻止 Spring OAuth2 工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50128057/

相关文章:

spring - oauth2 身份验证数据 blob 持久性方法的优缺点

java - SSLContext初始化

java - 使用 BigInteger

spring - 找到对多对多关系集合的共享引用

java - Spring Batch配置异常

java - HTTP 状态 500 - 预期 session 属性 'userObject'

java - 在首选项 fragment 中显示 Snackbar

java - 多种方法

java - 在用户不活动后使 spring 安全 session 过期

spring - 将 Null 传递给 Spring Security UserDetailsS​​ervice