SpringSecurity的@EnableWebSecurity注解SpringSecurity的@EnableWebSecurity注解
@EnableWebSecurity
@EnableWebSecurity是开启SpringSecurity的默认⾏为,它的上⾯有⼀个Import注解导⼊了WebSecurityConfiguration类,也就是说我们加上了@EnableWebSecurity这个注解,就是往IOC容器中注⼊了WebSecurityConfiguration这个类。
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE})
@Documented
@Import({WebSecurityConfiguration.class, SpringWebMvcImportSelector.class, OAuth2ImportSelector.class})
@EnableGlobalAuthentication
@Configuration
public @interface EnableWebSecurity {
boolean debug() default false;
}
它还有⼀个debug的功能,如果设置为true,则开启debug功能,每个经过那些过滤器都会被展⽰出来。
WebSecurityConfiguration
WebSecurityConfiguration⽤来配置初始化webSecurity的,在setFilterChainProxySecurityConfigurer⽅法中,它以配置SpringSecurity时继承⾃WebSecurityConfigurerAdapter的配置类来初始化SecurityConfigurer列表,来启⽤所需的安全策略
@Autowired(
required = false
)
public void setFilterChainProxySecurityConfigurer(ObjectPostProcessor<Object> objectPostProcessor, @Value("#{@autowiredWebSecurityConfigurersIgnoreP        this.webSecurity = (WebSecurity)objectPostProcessor.postProcess(new WebSecurity(objectPostProcessor));
if (this.debugEnabled != null) {
this.webSecurity.debug(this.debugEnabled);
}
webSecurityConfigurers.sort(WebSecurityConfiguration.AnnotationAwareOrderComparator.INSTANCE);
Integer previousOrder = null;
Object previousConfig = null;
Iterator var5;
SecurityConfigurer config;
for(var5 = webSecurityConfigurers.iterator(); var5.hasNext(); previousConfig = config) {
config = (();
Integer order = WebSecurityConfiguration.AnnotationAwareOrderComparator.lookupOrder(config);
if (previousOrder != null && previousOrder.equals(order)) {
throw new IllegalStateException("@Order on WebSecurityConfigurers must be unique. Order of " + order + " was already used on " + previousConfig +            }
previousOrder = order;
}
var5 = webSecurityConfigurers.iterator();
while(var5.hasNext()) {
config = (();
//将配置的每⼀个SecurityConfigurer列表传递给 webSecurity
this.webSecurity.apply(config);
}
this.webSecurityConfigurers = webSecurityConfigurers;
}
WebSecurityConfiguration这个类的创建流程也是经过spring容器初始化的那⼀整套。
所以在配置的时候,能拿到我们这个配置类⾥⾯的信息,具体如图:
接着创建过滤器链
//提供⼀个名叫springSecurityFilterChain的bean,返回⼀个Filter对象
@Bean(name = AbstractSecurityWebApplicationInitializer.DEFAULT_FILTER_NAME)
public Filter springSecurityFilterChain() throws Exception {
boolean hasConfigurers = webSecurityConfigurers != null
&& !webSecurityConfigurers.isEmpty();
if (!hasConfigurers) {
//如果没有配置过Spring Security,则会议WebSecurityConfigurerAdapter中的配置作为默认,上⾯能拿到我们的配置,因此就不⾛这段逻辑  WebSecurityConfigurerAdapter
WebSecurityConfigurerAdapter adapter = objectObjectPostProcessor
.postProcess(new WebSecurityConfigurerAdapter() {
});
webSecurity.apply(adapter);
}
return webSecurity.build();
}
以前在Spring的配置中,会有⼀个l,在⾥⾯配置过滤器,但是现在SpringBoot已经⾃动配置了l. DelegatingFilterProxy 是Spring提供的⼀个标准Servlet Filter代理,并代理改bean提供的过滤器,也就是说,在这个配置中,最终起作⽤的过滤器是什么完全取决于springSecurityFilterChain。
@Configuration(proxyBeanMethods = false)
@ConditionalOnWebApplication(type = Type.SERVLET)
@EnableConfigurationProperties(SecurityProperties.class)
@ConditionalOnClass({ AbstractSecurityWebApplicationInitializer.class, SessionCreationPolicy.class })
@AutoConfigureAfter(SecurityAutoConfiguration.class)
public class SecurityFilterAutoConfiguration {
private static final String DEFAULT_FILTER_NAME = AbstractSecurityWebApplicationInitializer.DEFAULT_FILTER_NAME;
@Bean
@ConditionalOnBean(name = DEFAULT_FILTER_NAME)
public DelegatingFilterProxyRegistrationBean securityFilterChainRegistration(
SecurityProperties securityProperties) {
DelegatingFilterProxyRegistrationBean registration = new DelegatingFilterProxyRegistrationBean(
DEFAULT_FILTER_NAME);
registration.Filter().getOrder());
registration.setDispatcherTypes(getDispatcherTypes(securityProperties));
spring ioc注解return registration;
}
private EnumSet<DispatcherType> getDispatcherTypes(SecurityProperties securityProperties) {
if (Filter().getDispatcherTypes() == null) {
return null;
}
Filter().getDispatcherTypes().stream()
.map((type) -> DispatcherType.valueOf(type.name()))
.Collection(() -> Of(DispatcherType.class)));
}
}
前⾯说的springSecurityFilterChain是由 webSecurity.build()这个创建的,最终调⽤的是doBuild⽅法,是由AbstractConfiguredSecurityBuilder提供的
public final O build() throws Exception {
if (this.buildingpareAndSet(false, true)) {
this.object = doBuild();
return this.object;
}
throw new AlreadyBuiltException("This object has already been built");
}
AbstractConfiguredSecurityBuilder的doBuild调⽤的是WebSecurity的performBuild()⽅法

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。