java 单机接口限流处理方案
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中,我们是这样写的。
在 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
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小时内删除侵权内容。
发表评论
暂时没有评论,来抢沙发吧~