Spring Boot

Spring Security增加登录退出日志

2020-03-11  本文已影响0人  EasyNetCN

基于Spring Boot 2.2.5 WebFlux。

下面代码实现了使用Form验证的时候,记录登录成功和退出登录的日志,当然也可以根据自己的业务需求,加入自己的逻辑。

Spring Security WebFlux中重写RedirectServerAuthenticationSuccessHandler(这个是默认的登录成功后的Handler)中onAuthenticationSuccess方法,实现自己的登录成功后的处理逻辑;重写SecurityContextServerLogoutHandler(这个是默认的退出登录后的handler)中logout,实现自己的退出登录的处理逻辑。

@EnableWebFluxSecurity
public class WebSecurityConfig {
    private static final Log logger = LogFactory.getLog(WebSecurityConfig.class);

    @Bean
    public PasswordEncoder passwordEncoder() {
        return PasswordEncoderFactories.createDelegatingPasswordEncoder();
    }

    @Bean
    public SecurityWebFilterChain springSecurityFilterChain(ServerHttpSecurity http, LogStreams logStreams) {
        http.csrf().disable().headers().frameOptions().mode(Mode.SAMEORIGIN).xssProtection().disable().and()
                .authorizeExchange()
                .pathMatchers("/css/**", "/fonts/**", "/img/**", "/js/**", "/actuator/**", "/login")
                .permitAll().anyExchange().authenticated().and().formLogin()
                .authenticationSuccessHandler(new RedirectServerAuthenticationSuccessHandler() {
                    @Override
                    public Mono<Void> onAuthenticationSuccess(WebFilterExchange webFilterExchange,
                            Authentication authentication) {
                        try {
                            var userDetail = SecurityUtility.getUserDetails(authentication);

                            createSystemLog(logStreams, "登录", "登录", userDetail,
                                    HttpUtility.clientIp(webFilterExchange.getExchange().getRequest()));
                        } catch (Exception ex) {
                            logger.error(ex);
                        }

                        return super.onAuthenticationSuccess(webFilterExchange, authentication);
                    }

                }).loginPage("/login").and().logout().logoutHandler(new SecurityContextServerLogoutHandler() {
                    @Override
                    public Mono<Void> logout(WebFilterExchange exchange, Authentication authentication) {
                        try {
                            var userDetail = SecurityUtility.getUserDetails(authentication);

                            createSystemLog(logStreams, "首页", "退出登录", userDetail,
                                    HttpUtility.clientIp(exchange.getExchange().getRequest()));
                        } catch (Exception ex) {
                            logger.error(ex);
                        }

                        return super.logout(exchange, authentication);
                    }
                });

        return http.build();
    }

    private void createSystemLog(LogStreams logStreams, String moduleName, String operateContent,
            CloudUserDetails userDetail, String ip) {
        var messageChannel = logStreams.outboundLogStreams();

        var appSystemLog = new AppSystemLog();

        appSystemLog.setApplicationId(3L);
        appSystemLog.setEnterpriseId(0L);
        appSystemLog.setIp(ip);
        appSystemLog.setModuleId(0L);
        appSystemLog.setModuleName(moduleName);
        appSystemLog.setUsername(userDetail.getUsername());
        appSystemLog.setOperatorId(userDetail.getUserId());
        appSystemLog.setOperatorName(userDetail.getName());
        appSystemLog.setOperateContent(operateContent);
        appSystemLog.setOperateParam("");
        appSystemLog.setOperateTime(LocalDateTime.now());

        messageChannel.send(MessageBuilder.withPayload(appSystemLog)
                .setHeader(MessageHeaders.CONTENT_TYPE, MimeTypeUtils.APPLICATION_JSON)
                .setHeader("partitionKey", "app-system-logs").build());
    }
}
上一篇 下一篇

猜你喜欢

热点阅读