1 SecurityContextPersistenceFilter
通过观察Filter的名字,就能大概猜出来这个过滤器的作用,持久化SecurityContext实例org.springframework.security.web.context.SecurityContextPersistenceFilter
该 Filter 位于过滤器的顶端,所有过滤器的入口
public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException { HttpServletRequest request = (HttpServletRequest) req; HttpServletResponse response = (HttpServletResponse) res; if (request.getAttribute(FILTER_APPLIED) != null) { // 确保对于每个请求只应用一次过滤器 chain.doFilter(request, response); return; } final boolean debug = logger.isDebugEnabled(); request.setAttribute(FILTER_APPLIED, Boolean.TRUE); if (forceEagerSessionCreation) { HttpSession session = request.getSession(); if (debug && session.isNew()) { logger.debug("Eagerly created session: " + session.getId()); } } // 将 request/response 对象交给HttpRequestResponseHolder维持 HttpRequestResponseHolder holder = new HttpRequestResponseHolder(request,response); //通过SecurityContextRepository接口的实现类装载SecurityContext实例 //HttpSessionSecurityContextRepository将产生SecurityContext实例的任务交给SecurityContextHolder.createEmptyContext() //SecurityContextHolder再根据策略模式的不同, //把任务再交给相应策略类完成SecurityContext的创建 //如果没有配置策略名称,则默认为 //ThreadLocalSecurityContextHolderStrategy, //该类直接通过new SecurityContextImpl()创建实例 SecurityContext contextBeforeChainExecution = repo.loadContext(holder); try { //将产生的SecurityContext再通过SecurityContextHolder-> //ThreadLocalSecurityContextHolderStrategy设置到ThreadLocal SecurityContextHolder.setContext(contextBeforeChainExecution); //继续把请求流向下一个过滤器执行 chain.doFilter(holder.getRequest(), holder.getResponse()); } finally { //先从SecurityContextHolder获取SecurityContext实例 SecurityContext contextAfterChainExecution = SecurityContextHolder .getContext(); //关键性地除去SecurityContextHolder内容 - 在任何事情之前执行此操作 //再把SecurityContext实例从SecurityContextHolder中清空 //若没有清空,会受到服务器的线程池机制的影响 SecurityContextHolder.clearContext(); //将SecurityContext实例持久化到session中 repo.saveContext(contextAfterChainExecution, holder.getRequest(), holder.getResponse()); request.removeAttribute(FILTER_APPLIED); if (debug) { logger.debug("SecurityContextHolder now cleared, as request processing completed"); } } }
通过源码中的注释,应该可以看出来,这个Filter的作用主要是创建一个空的SecurityContext(如果session中没有SecurityContext实例),然后持久化到session中。
作者:芥末无疆sss
链接:https://www.jianshu.com/p/a3630169351e
來源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。