我正在使用Spring Security 4.0.1,并希望使用多个身份验证提供程序使用基于Java的配置进行身份验证。如何指定提供程序顺序?
我希望使用AuthenticationManagerBuilder,因为这就是<code>WebSecurityConfigurerAdapter。configureGlobal()公开,但我看不到任何指定顺序的方法。我需要手动创建ProviderManager吗?
更新:这是基于Arun的答案的问题澄清。我想使用的特定提供程序是用于自定义UserService
的ActiveDirectoryLdapAuthenticationProvider
和DaoAuthenticationProvider
。
最终,我想首先针对Dao Auth的提供程序
进行身份验证,然后针对ActiveDirectoryLdapAuth的提供程序
进行身份验证。
AD 提供程序涉及对 AuthenticationManagerBuilder.authenticationProvider() 的调用,但 DAO 提供程序涉及调用 AuthenticationManagerBuilder.userService(),
这会在幕后围绕用户服务创建 DaoAuthenticationProvider
。查看源代码,它不会直接将提供程序放在提供程序列表中(它创建了一个配置器),因此 Arun 的答案在这里对我不起作用。
我尝试手动创建DaoAuthenticationProvider
,并将其传递给authenticationProvider()
。这没有影响订单。
我在Spring 5应用程序中遇到了完全相同的问题,但是在我的情况下,创建DaoAuthenticationProvider
有所帮助。这是我的代码(我省略了很多代码并粘贴了最重要的代码)。
...
import javax.annotation.PostConstruct;
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true)
@Import(SecurityProblemSupport.class)
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
private final Logger log = LoggerFactory.getLogger(SecurityConfiguration.class);
private final AuthenticationManagerBuilder authenticationManagerBuilder;
private final UserDetailsService userDetailsService;
private final TokenProvider tokenProvider;
private final CorsFilter corsFilter;
private final SecurityProblemSupport problemSupport;
public SecurityConfiguration(AuthenticationManagerBuilder authenticationManagerBuilder, UserDetailsService userDetailsService, TokenProvider tokenProvider, CorsFilter corsFilter, SecurityProblemSupport problemSupport) {
this.authenticationManagerBuilder = authenticationManagerBuilder;
this.userDetailsService = userDetailsService;
this.tokenProvider = tokenProvider;
this.corsFilter = corsFilter;
this.problemSupport = problemSupport;
}
@PostConstruct
public void init() {
try {
authenticationManagerBuilder.authenticationProvider(userDetailsAuthenticationProvider());
if (isSsoEnabled()) {
authenticationManagerBuilder
.authenticationProvider(activeDirectoryLdapAuthenticationProvider());
}
if (isKerberosEnabled()) {
authenticationManagerBuilder
.authenticationProvider(kerberosServiceAuthenticationProvider());
}
} catch (Exception e) {
throw new BeanInitializationException("Security configuration failed", e);
}
}
@Bean
public DaoAuthenticationProvider userDetailsAuthenticationProvider() {
DaoAuthenticationProvider authProvider
= new DaoAuthenticationProvider();
authProvider.setUserDetailsService(userDetailsService);
authProvider.setPasswordEncoder(passwordEncoder());
return authProvider;
}
@Override
@Bean
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
@Bean
public PasswordEncoder passwordEncoder() {
return new CustomPasswordEncoder();
}
@Override
public void configure(WebSecurity web) throws Exception {
...
}
@Override
protected void configure(HttpSecurity http) throws Exception {
...
}
private JWTConfigurer securityConfigurerAdapter() {
return new JWTConfigurer(tokenProvider);
}
private ActiveDirectoryLdapAuthenticationProvider activeDirectoryLdapAuthenticationProvider() {
ActiveDirectoryLdapAuthenticationProvider provider =
new ActiveDirectoryLdapAuthenticationProvider(getAdDomain(), getAdServer());
provider.setUserDetailsContextMapper((UserDetailsContextMapper) userDetailsService);
return provider;
}
private boolean isSsoEnabled() {
return Boolean.parseBoolean(ConfigurationFileUtils.getConfigurationProperty("security.use-sso"));
}
private boolean isKerberosEnabled() {
return isSsoEnabled() && Boolean.parseBoolean(ConfigurationFileUtils.getConfigurationProperty("security.use-kerberos"));
}
}
没有明确的订购条款。调用的顺序将是您向AuthenticationManagerBuilder.AuthenticationProvider()
提供AuthentiationProvider
例如
auth.authenticationProvider(getAuthenticationProvider2());
auth.authenticationProvider(getAuthenticationProvider1());
将导致以下调用顺序
和
auth.authenticationProvider(getAuthenticationProvider1());
auth.authenticationProvider(getAuthenticationProvider2());
将导致以下顺序的调用
身份验证提供者1,身份验证提供者2
我在configure方法中尝试了objectPostProcessor,它工作了。不确定这是否是您想要的:
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.jdbcAuthentication().dataSource(dataSource)
.passwordEncoder(new BCryptPasswordEncoder());
auth.authenticationProvider(new CustomAuthenticationProvider(this.dataSource));
auth.objectPostProcessor(new ObjectPostProcessor<Object>() {
@Override
public <O> O postProcess(O object) {
ProviderManager providerManager = (ProviderManager) object;
Collections.swap(providerManager.getProviders(), 0, 1);
return object;
}
});
}
这是在您的WebSecurityCon的继承类上的配置方法。
使用对象后处理器的原因是,我们需要等待AuthenticationManagerBuilder实际构建对象,然后才能访问和更改提供者列表的顺序。
希望有帮助…如果你有任何问题,请告诉我。
我使用的是Spring Boot 2.0(利用Spring Security 5.0)。我正在尝试向WebSecurityConfigureAdapter子类中的AuthenticationManager添加自定义AuthenticationProvider。如果我重写configure(AuthenticationManagerBuilder)方法来提供我的新提供者,那么我不知道如何将Authe
我已经创建了身份提供程序,并且从浏览器中它工作正常。 参考:密钥斗篷身份提供程序后代理登录抛出错误 从浏览器,我可以使用外部IDP登录,如果外部IDP用户不在keycloak中,它会在keyclock中创建,这绝对没问题,并重定向到仪表板。 但我的问题是,我们如何用keycloak rest api实现这个流程? 是否有任何api用于使用外部IDP登录,并将获得外部IDP的令牌以及密钥斗篷的令牌?
我正在使用pact-jvm提供程序Spring。我有两个不同的pact(.json)文件,比如(order.json和irs.json),我需要按顺序运行它们(order后面是irs),但是根据字母顺序选择测试类,irs首先运行,order其次运行。是否有方法调用、执行特定的测试类提供程序状态或定义测试类执行顺序?
本文向大家介绍F# 使用CSV类型提供程序,包括了F# 使用CSV类型提供程序的使用技巧和注意事项,需要的朋友参考一下 示例 给定以下CSV文件: 您可以使用以下脚本读取数据:
我正在尝试使用pact来验证spring boot微服务。我已经从consumer生成了pact文件,并在provider端使用pact Broker验证了它。 我有另一个用例,在根据实际的服务响应验证pact文件之前,我需要执行一些代码。我读过关于状态改变URL和状态改变与闭包来实现它,但没有得到一个如何实现这一点的例子。有人能帮忙吗? 如果这个客户不存在,那么我将需要通过读取pact文件中的更
我已经在文件中添加了所有相关build.gradle依赖项。尽管如此,当我尝试运行调用SOAP服务时,还是会出现以下错误。共享依赖项部分和错误详细信息。使用Java11。网上已经有很多答案,但似乎都不起作用。任何帮助/建议将是值得赞赏的。 低于错误跟踪