spring security @EnableWebSecurity自动配置DaoAuthenticationProvider流程

2024-01-16 08:53:42 浏览数 (2)

版本

spring-security:6.2.1

满足下列情况时,spring-security会自动配置DaoAuthenticationProvider

  • 使用@EnableWebSecurity
  • 注册UserDetailsServiceBean
  • 没有注册其他AuthenticationProvider类型的Bean
  • 没有通过http.authenticationProvider配置

源码

org.springframework.security.config.annotation.web.configuration.EnableWebSecurity

代码语言:javascript复制
// 导入全局认证配置
@EnableGlobalAuthentication
public @interface EnableWebSecurity {}

org.springframework.security.config.annotation.authentication.configuration.EnableGlobalAuthentication

代码语言:javascript复制
// 导入认证配置
@Import(AuthenticationConfiguration.class)
public @interface EnableGlobalAuthentication {}

org.springframework.security.config.annotation.authentication.configuration.AuthenticationConfiguration

代码语言:javascript复制
public class AuthenticationConfiguration {
	...
	@Bean
	public static InitializeUserDetailsBeanManagerConfigurer initializeUserDetailsBeanManagerConfigurer(
			ApplicationContext context) {
		return new InitializeUserDetailsBeanManagerConfigurer(context);
	}
	...
}

org.springframework.security.config.annotation.authentication.configuration.InitializeUserDetailsBeanManagerConfigurer

代码语言:javascript复制
@Order(InitializeUserDetailsBeanManagerConfigurer.DEFAULT_ORDER)
class InitializeUserDetailsBeanManagerConfigurer extends GlobalAuthenticationConfigurerAdapter {
	...
	@Override
	public void init(AuthenticationManagerBuilder auth) throws Exception {
		auth.apply(new InitializeUserDetailsManagerConfigurer());
	}
	class InitializeUserDetailsManagerConfigurer extends GlobalAuthenticationConfigurerAdapter {
		@Override
		public void configure(AuthenticationManagerBuilder auth) throws Exception {
			if (auth.isConfigured()) { // 如果认证提供者不为空(通过httpSecurity配置了认证提供者,或者注册了AuthenticationProvider类型的Bean),或者上级的认证管理器不为空则跳过
				return;
			}
			UserDetailsService userDetailsService = getBeanOrNull(UserDetailsService.class);
			if (userDetailsService == null) { // 如果没有注册 UserDetailsService Bean则跳过
				return;
			}
			// 获取密码编码器 Bean
			PasswordEncoder passwordEncoder = getBeanOrNull(PasswordEncoder.class);
			// 获取 UserDetailsPasswordService Bean (用于密码重新编码)
			UserDetailsPasswordService passwordManager = getBeanOrNull(UserDetailsPasswordService.class);
			// 创建并注册 DaoAuthenticationProvider 
			DaoAuthenticationProvider provider = new DaoAuthenticationProvider();
			provider.setUserDetailsService(userDetailsService);
			if (passwordEncoder != null) {
				provider.setPasswordEncoder(passwordEncoder);
			}
			if (passwordManager != null) {
				provider.setUserDetailsPasswordService(passwordManager);
			}
			provider.afterPropertiesSet();
			auth.authenticationProvider(provider);
		}
	}
	...
}

org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder

代码语言:javascript复制
public class AuthenticationManagerBuilder
		extends AbstractConfiguredSecurityBuilder<AuthenticationManager, AuthenticationManagerBuilder>
		implements ProviderManagerBuilder<AuthenticationManagerBuilder> {
		...
		public boolean isConfigured() {
			return !this.authenticationProviders.isEmpty() || this.parentAuthenticationManager != null;
		}
		...
}

0 人点赞