zoukankan      html  css  js  c++  java
  • Springsecurity源码Filter之LogoutFilter(十三)

    负责处理登出相关逻辑,默认url映射是/logout

    org.springframework.security.config.annotation.web.configurers.LogoutConfigurer 初始化

    默认初始化处https://www.cnblogs.com/LQBlog/p/15508248.html#autoid-12-0-0

    private void applyDefaultConfiguration(HttpSecurity http) throws Exception {
            //http本质也是build 这里都是配置默认的config configure add CsrfConfigurer
            http.csrf();
            //默认增加一个WebAsyncManagerIntegrationFilter
            http.addFilter(new WebAsyncManagerIntegrationFilter());
            //configures add ExceptionHandlingConfigurer
            http.exceptionHandling();
            //configures add HeadersConfigurer
            http.headers();
            //configures add SessionManagementConfigurer
            http.sessionManagement();
            //configure add SecurityContextConfigurer
            http.securityContext();
            //configure add RequestCacheConfigurer
            http.requestCache();
            ///configure add AnonymousConfigurer
            http.anonymous();
            ///configure add ServletApiConfigurer
            http.servletApi();
            //configure DefaultLoginPageConfigurer
            http.apply(new DefaultLoginPageConfigurer<>());
            //configure LogoutConfigurer
            http.logout();
        }

    通过http.logout().addLogoutHandler() 可以自定义handler

    LogoutFilter

        private void doFilter(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
                throws IOException, ServletException {
            //匹配是否能够处理 默认是/logout
            if (requiresLogout(request, response)) {
                //从SecurityContextHolder 获得Authentication信息
                Authentication auth = SecurityContextHolder.getContext().getAuthentication();
                if (this.logger.isDebugEnabled()) {
                    this.logger.debug(LogMessage.format("Logging out [%s]", auth));
                }
                /**
                 * 调用CompositeLogoutHandler 他也实现了LogoutHandler 他只是一个统一的管理器
                 * 内部循环调用LogoutHandler
                 * 默认有三种
                 * PersistentTokenBasedRememberMeServices <1>
                 * SecurityContextLogoutHandler <2>
                 * LogoutSuccessEventPublishingLogoutHandler<3>
                 */
                this.handler.logout(request, response, auth);
                //处理登出成功的SimpleUrlLogoutSuccessHandler 比如重定向到登录页
                this.logoutSuccessHandler.onLogoutSuccess(request, response, auth);
                return;
            }
            chain.doFilter(request, response);
        }

    <1>

    org.springframework.security.web.authentication.rememberme.PersistentTokenBasedRememberMeServices#logout

        @Override
        public void logout(HttpServletRequest request, HttpServletResponse response, Authentication authentication) {
            //清除cookile
            super.logout(request, response, authentication);
            if (authentication != null) {
                //删除token
                this.tokenRepository.removeUserTokens(authentication.getName());
            }
        }

    <2>

    org.springframework.security.web.authentication.logout.SecurityContextLogoutHandler#logout

     @Override
        public void logout(HttpServletRequest request, HttpServletResponse response, Authentication authentication) {
            Assert.notNull(request, "HttpServletRequest required");
            if (this.invalidateHttpSession) {
                HttpSession session = request.getSession(false);
                if (session != null) {
                    //清空session
                    session.invalidate();
                    if (this.logger.isDebugEnabled()) {
                        this.logger.debug(LogMessage.format("Invalidated session %s", session.getId()));
                    }
                }
            }
            if (this.clearAuthentication) {
                //清空
                SecurityContext context = SecurityContextHolder.getContext();
                context.setAuthentication(null);
            }
            //清空
            SecurityContextHolder.clearContext();
        }

    <3>

    发布一个spring的事件我们可以监听这个事件 知道某个用户登出了 参考:https://www.cnblogs.com/LQBlog/p/13878553.html#_label5

    org.springframework.security.web.authentication.logout.LogoutSuccessEventPublishingLogoutHandler#logout

    @Override
        public void logout(HttpServletRequest request, HttpServletResponse response, Authentication authentication) {
            if (this.eventPublisher == null) {
                return;
            }
            if (authentication == null) {
                return;
            }
            this.eventPublisher.publishEvent(new LogoutSuccessEvent(authentication));
        }
  • 相关阅读:
    C# 字段 属性 方法 三霸主齐上阵
    C# 项目之总结,浓缩才是精华
    C# 语法 重中之重
    岁月流逝,C#成为我们IT精英永恒不变的经典
    pv:快餐厅4类职员正确并发运行的程序——用pv实现有向图的前驱关系哦!
    pv错题:用pv操作实现旅客,汽车之间的同步关系——北航2018考研计算机!!!!!!!!我还很不熟练,奋斗吧少年!!!!!!
    windows 的 DMA
    pv打卡:生产者消费者问题扩展——>南航2002pv习题哦
    冷门的OS知识:中断——这个我多大熟练qwq!
    Unix混合索引结构_文件系统_文件的组织_文件的物理结构_多级索引文件——>相关的小计算题!!!!!!重点重点重点!!!!!!
  • 原文地址:https://www.cnblogs.com/LQBlog/p/15533703.html
Copyright © 2011-2022 走看看