Spring Security过滤器链加载执行流程源码解析

网友投稿 499 2022-09-05


Spring Security过滤器链加载执行流程源码解析

目录Spring Security实现原理一、Spring Security过滤器链加载1、注册名为 springSecurityFilterChain的过滤器2、查看 DelegatingFilterProxy类3、查看 FilteUkHNMzGFwkrChainProxy类3.1 查看 doFilterInternal方法。3.2 查看 getFilters方法。4 查看 SecurityFilterChain接口5 查看 SpringBootWebSecurityConfiguration类二、过滤器链的执行流程1、调用 OncePerRequestFilter过滤器2、查看 FilterChainProxy过滤器3、查看 FilterSecurityInterceptor过滤器三、Spring Security常见过滤器

Spring Security实现原理

Spring Security 采用 IoC 和 AOP思想,基于 Servlet 过滤器实现的安全框架、为 Web 请求和方法调用提供身份确认和授权处理,还提供与其他库的集成以简化其使用,避免了代码耦合,减少了大量重复代码工作。

在之前 web.xml中,我们是这样写的。

springSecurityFilterChain

org.springframework.web.filter.DelegatingFilterProxy

springSecurityFilterChain

/*

在 Spring Boot项目之后,我们引入 Spring Security依赖,什么也没做,启动项目 Spring Security 就会生效,访问请求就进行了拦截。

Spring Boot 对于 Spring Security 提供了自动化配置方案,可以使用更少的配置来使用 Shttp://pring Security。那么这个过滤器链是怎么加载和实现拦截的呢?

一、Spring Security过滤器链加载

1、注册名为 springSecurityFilterChain的过滤器

当 Spring Boot 项目启动后,SecurityFilterAutoConfiguration类会加载 DelegatingFilterProxyRegistrationBean注册过滤器,名字为 springSecurityFilterChain。

注意:springSecurityFilterChain名字是固定写死的。

DelegatingFilterProxyRegistrationBean 注册成功后,该过滤器就被加载了到了注册器中。注册器注册了所有的过滤器后,会为每个过滤器生成 DelegatingFilterProxy代理对象并注册到 IoC中 。

2、查看 DelegatingFilterProxy类

我们访问项目,就会进入 DelegatingFilterProxy类的 doFilter方法。

DelegatingFilterProxy类本质也是一个 Filter,其间接实现了 Filter接口,但是在 doFilter中其实调用的从 Spring 容器中获取到的代理 Filter的实现类。

返回的 FilterChainProxy对象。由此可知,DelegatingFilterProxy类通过 springSecurityFilterChain这个名称,得到了一个 FilterChainProxy过滤器,最终执行的是这个过滤器的 doFilter方法。

1)验证 springSecurityFilterChain名词不能修改查看 initDelegate方法。

3、查看 FilterChainProxy类

FilterChainProxy类本质也是一个 Filter,所以查看 doFilter方法。留意该类里面的属性。

public class FilterChainProxy extends GenericFilterBean {

private static final Log logger = LogFactory.getLog(FilterChainProxy.class);

private static final String FILTER_APPLIED =

FilterChainProxy.class.getName().concat(".APPLIED");

// 过滤器链

private List filterChains;

private FilterChttp://hainProxy.FilterChainValidator filterChainValidator;

private HttpFirewall firewall;

3.1 查看 doFilterInternal方法。

惊不惊喜?15个过滤器都在这里了!

3.2 查看 getFilters方法。

原来这些过滤器都被封装进 SecurityFilterChain对象中。

4 查看 SecurityFilterChain接口

SecurityFilterChain类是个接口,实现类也只有一个 DefaultSecurityFilterChain类。DefaultSecurityFilterChain类的构造方法,初始化了 List filters,是通过传参放进去的。

过滤器链参数是什么时候传入的?

5 查看 SpringBootWebSecurityConfiguration类

创建 Spring Security 过滤器链是交给 Spring boot 自动配置,由 SpringBootWebSecurityConfiguration类创建注入。

查看 WebSecurityConfigurerAdapter类。

然后会注入 HttpSecurity对象,HttpSecurity可以理解为 Spring Security 的 http核心配置,存放 Spring Security 中的过滤器链、请求匹配路径等相关认证授权的重要方法。

然后开始创建 Spring Security 过滤器链了,是交给 Spring Boot自动配置,一共有 15个过滤器。使用 OrderedFilter进行代理,并设置了order属性。添加完成后,将这些过滤器再封装为 DefaultSecurityFilterChain对象。

最后通过 WebSecurityConfiguration配置加载 springSecurityFilterChain,WebSecurityConfiguration中维护了securityFilterChains属性,会存放过滤器链中所有的过滤器。

总结:Spring boot 通过 DelegatingFilterProxyRegistrationBean注册过滤器,名字为 springSecurityFilterChain,并生成 DelegatingFilterProxy代理对象并注册到 IoC中。最终真正调用 FilterChainProxy过滤器的http:// doFilter 获取到 Spring Security 过滤器链。

Spring Security的过滤器链在底层是封装在 SecurityFilterChain接口中的。

二、过滤器链的执行流程

1、调用 OncePerRequestFilter过滤器

首先进入的是 OncePerRequestFilter 过滤器。OncePerRequestFilter是为了确保一次请求中只通过一次filter,而不需要重复的执行。

会进入 DelegatingFilterProxy代理对象中 invokeDelegate方法,实际真正执行的是 FilterChainProxy过滤器的 doFilter 方法。

2、查看 FilterChainProxy过滤器

查看 FilterChainProxy过滤器中的 doFilterInternal方法。然后首先进入FilterChainProxy中的 doFilterInternal方法。doFilterInternal方法中会调用 getFilters方法,会从过滤器链中拿出所有的拦截器。

然后创建一个 VirtualFilterChain对象,一个虚拟的过滤器链,并执行其中的 doFilter 方法。使用过滤器对当前请求进行层层过滤。

3、查看 FilterSecurityInterceptor过滤器

最后进入到 FilterSecurityInterceptor过滤器中,该过滤器是过滤器链的最后一个过滤器,invoke方法中。

先调用父类的 beforeInvocation方法,之后调用 filterChain的 doFilter方法,之后调用父类的 finallyInvocation和afterInvocation方法。

在 beforeInvocation方法中,如果当前的请求没有通过认证,会抛出 Access is denied异常,这个异常会被ExceptionTranslationFilter过滤器处理。如果抛出的异常是 AuthenticationException,则执行方法sendStartAuthentication方法。最终调用 EntryPoint的 commence方法,发布异常。

三、Spring Security常见过滤器

1、WebAsyncManagerIntegrationFilter

org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter

其主要用于集成 SecurityContext到 Spring异步执行机制中的 WebAsyncManager。

2、SecurityContextPersistenceFilter

org.springframework.security.web.context.SecurityContextPersistenceFilter

其主要是使用 SecurityContextRepository在 session中保存或更新一个SecurityContext,并将 SecurityContext给以后的过滤器使用,来为后续 filter建立所需的上下文。SecurityContext中存储了当前用户的认证以及权限信息。

3、HeaderWriterFilter

org.springframework.security.web.header.HeaderWriterFilter

其主要是向请求的 Header中添加相应的信息,可在 http标签内部使用 security:headers来控制。

4、CsrfFilter

org.springframework.security.web.csrf.CsrfFilter

csrf又称跨域请求伪造,SpringSecurity会对所有 post请求验证是否包含系统生成的 csrf的 token信息,如果不包含,则报错。起到防止csrf攻击的效果。

5、LogoutFilter

org.springframework.security.web.authentication.logout.LogoutFilter

其主要用于实现用户退出,清除认证信息。默认匹配 URL为 /logout的请求。

6、UsernamePasswordAuthenticationFilter

org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter

其主要用于认证操作,默认匹配URL为 /login且必须为POST请求。

7、DefaultLoginPageGeneratingFilter

org.springframework.security.web.authentication.ui.DefaultLoginPageGeneratingFilter

如果没有在配置文件中指定认证页面,则由该过滤器生成一个默认认证页面。

8、DefaultLogoutPageGeneratingFilter

org.springframework.security.web.authentication.ui.DefaultLogoutPageGeneratingFilter

由此过滤器可以生产一个默认的退出登录页面

9、BasicAuthenticationFilter

org.springframework.security.web.authentication.BasicAuthenticationFilter

此过滤器会自动解析 HTTP请求中头部名字为 Authentication,且以 Basic开头的头信息。

10、RequestCacheAwareFilter

org.springframework.security.web.savedrequest.RequestCacheAwareFilter

通过HttpSessionRequestCache内部维护了一个 RequestCache,用于缓存 HttpServletRequest。

11、SecurityContextHolderAwareRequestFilter

org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter

针对 ServletRequest进行了一次包装,使得 request具有更加丰富的 API。

12、AnonymousAuthenticationFilter

org.springframework.security.web.authentication.AnonymousAuthenticationFilter

当 SecurityContextHolder中认证信息为空,则会创建一个匿名用户存入到 SecurityContextHolder中。Spring Security为了兼容未登录的访问,也走了一套认证流程,只不过是一个匿名的身份。

13、SessionManagementFilter

org.springframework.security.web.session.SessionManagementFilter

其主要用于限制同一用户开启多个会话的数量。

14、ExceptionTranslationFilter

org.springframework.security.web.access.ExceptionTranslationFilter

异常转换过滤器位于整个 springSecurityFilterChain的后方,用来转换整个链路中出现的异常。ExceptionTranslationFilter过滤器会拦截处理 AccessDeniedException和 AuthenticationException并添加到HTTP响应中。

15、FilterSecurityInterceptor

org.springframework.security.web.access.intercept.FilterSecurityInterceptor

获取所配置资源访问的授权信息,根据 SecurityContextHolder中存储的用户信息来决定其是否有权限。


版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:【特征选择】基于亨利气体溶解度优化算法求解二进制特征选择问题(HGSO)含Matlab源码
下一篇:【灰狼算法】基于混合灰狼算法求解单目标优化问题附matlab代码(灰狼优化算法百科)
相关文章

 发表评论

暂时没有评论,来抢沙发吧~