CRM客户管理系统Config配置类和Listener和Filter------CRM项目

package com.alatus.config.filter;

import com.alatus.constant.Constants;
import com.alatus.model.TUser;
import com.alatus.result.Result;
import com.alatus.service.RedisService;
import com.alatus.util.JSONUtils;
import com.alatus.util.JWTUtils;
import com.alatus.util.ResponseUtils;
import com.alatus.result.CodeEnum;
import jakarta.annotation.Resource;
import jakarta.servlet.FilterChain;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.filter.OncePerRequestFilter;

import java.io.IOException;
import java.util.concurrent.TimeUnit;

@Component
public class TokenVerifyFilter extends OncePerRequestFilter {

    @Resource
    private RedisService redisService;
//    @Resource
//    //    springboot框架提供的线程池,ioc容器内已经存在
//    private ThreadPoolTaskExecutor threadPoolTaskExecutor;
    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {
        if (request.getRequestURI().equals(Constants.LOGIN_URI)) { //如果是登录请求,此时还没有生成jwt,那不需要对登录请求进行jwt验证
            //验证jwt通过了 ,让Filter链继续执行,也就是继续执行下一个Filter
            filterChain.doFilter(request, response);
        } else {
            String token;
            if(request.getRequestURI().equals(Constants.EXPORT_EXCEL_URI)){
                token = request.getParameter(Constants.TOKEN_NAME);
            }
            else{
                token = request.getHeader(Constants.TOKEN_NAME);
            }
            if(!StringUtils.hasText(token)){
//                没拿到token,将失败这个枚举传回去,解析并取出常量拼接
                Result result = Result.FAIL(CodeEnum.TOKEN_IS_EMPTY);
//                封装
                String resultJSON = JSONUtils.toJSON(result);
//                返回
                ResponseUtils.write(response,resultJSON);
                return;
            }
//            验证token有没有被篡改过,也是验证token合法性
            if (!(JWTUtils.verifyJWT(token))){
//                token不合法
                Result result = Result.FAIL(CodeEnum.TOKEN_IS_NONE_MATCH);
//                封装
                String resultJSON = JSONUtils.toJSON(result);
//                返回
                ResponseUtils.write(response,resultJSON);
                return;
            }
            TUser tUser = JWTUtils.parseUserFromJWT(token);
            String redisToken = (String) redisService.getValue(Constants.REDIS_JWT_KEY + tUser.getId());
            if(!StringUtils.hasText(redisToken)){
//                没有获取到内容说明token过期了
                Result fail = Result.FAIL(CodeEnum.TOKEN_IS_EXPIRED);
                String json = JSONUtils.toJSON(fail);
                ResponseUtils.write(response,json);
                return;
            }
            if (!redisToken.equals(token)) {
//                登陆失败token错误
                Result result = Result.FAIL(CodeEnum.TOKEN_IS_ERROR);
//                把R对象转为JSON
                String json = JSONUtils.toJSON(result);
                ResponseUtils.write(response,json);
                return;
            }
//            jwt验证通过了
            UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(tUser,tUser.getLoginPwd(),tUser.getAuthorities());
            SecurityContextHolder.getContext().setAuthentication(authenticationToken);
//            刷新一下token
//            做异步执行
//            new Thread(new Runnable() {
//                @Override
//                public void run() {
                    这里刷新token即可
                    从请求头中获取
//                    String rememberMe = request.getHeader("rememberMe");
//                    if (!Boolean.parseBoolean(rememberMe)) {
//                        redisService.expire(Constants.REDIS_JWT_KEY + tUser.getId(), Constants.DEFAULT_EXPIRE_TIME, TimeUnit.SECONDS);
//                    }
//                }
//            }).start();
//            最好使用线程池的方式去执行
//            threadPoolTaskExecutor.execute(() -> {
//                    这里刷新token即可
//                    从请求头中获取
//                    String rememberMe = null;
//                    if(StringUtils.hasText(request.getHeader(Constants.REMEMBER_ME))){
//                        rememberMe = request.getHeader(Constants.REMEMBER_ME);
//                    }
//                    if (!Boolean.parseBoolean(rememberMe)) {
//                        redisService.expire(Constants.REDIS_JWT_KEY + tUser.getId(), Constants.DEFAULT_EXPIRE_TIME, TimeUnit.SECONDS);
//                    }
//            });
//            验证jwt通过了,让filter链继续执行


//            经过实验,线程池有概率导致请求和我们的service走的线程不是同一个导致请求头里面获取这个rememberMe报错
//            还是不用线程为好,慢点就慢点吧
            String rememberMe = null;
            if(StringUtils.hasText(request.getHeader(Constants.REMEMBER_ME))){
                rememberMe = request.getHeader(Constants.REMEMBER_ME);
            }
            if (!Boolean.parseBoolean(rememberMe)) {
                redisService.expire(Constants.REDIS_JWT_KEY + tUser.getId(), Constants.DEFAULT_EXPIRE_TIME, TimeUnit.SECONDS);
            }
            filterChain.doFilter(request,response);
        }
    }
}

package com.alatus.config.filter;

import com.alatus.constant.Constants;
import com.alatus.model.TUser;
import com.alatus.result.Result;
import com.alatus.service.RedisService;
import com.alatus.util.JSONUtils;
import com.alatus.util.JWTUtils;
import com.alatus.util.ResponseUtils;
import com.alatus.result.CodeEnum;
import jakarta.annotation.Resource;
import jakarta.servlet.FilterChain;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.filter.OncePerRequestFilter;

import java.io.IOException;
import java.util.concurrent.TimeUnit;

@Component
public class TokenVerifyFilter extends OncePerRequestFilter {

    @Resource
    private RedisService redisService;
//    @Resource
//    //    springboot框架提供的线程池,ioc容器内已经存在
//    private ThreadPoolTaskExecutor threadPoolTaskExecutor;
    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {
        if (request.getRequestURI().equals(Constants.LOGIN_URI)) { //如果是登录请求,此时还没有生成jwt,那不需要对登录请求进行jwt验证
            //验证jwt通过了 ,让Filter链继续执行,也就是继续执行下一个Filter
            filterChain.doFilter(request, response);
        } else {
            String token;
            if(request.getRequestURI().equals(Constants.EXPORT_EXCEL_URI)){
                token = request.getParameter(Constants.TOKEN_NAME);
            }
            else{
                token = request.getHeader(Constants.TOKEN_NAME);
            }
            if(!StringUtils.hasText(token)){
//                没拿到token,将失败这个枚举传回去,解析并取出常量拼接
                Result result = Result.FAIL(CodeEnum.TOKEN_IS_EMPTY);
//                封装
                String resultJSON = JSONUtils.toJSON(result);
//                返回
                ResponseUtils.write(response,resultJSON);
                return;
            }
//            验证token有没有被篡改过,也是验证token合法性
            if (!(JWTUtils.verifyJWT(token))){
//                token不合法
                Result result = Result.FAIL(CodeEnum.TOKEN_IS_NONE_MATCH);
//                封装
                String resultJSON = JSONUtils.toJSON(result);
//                返回
                ResponseUtils.write(response,resultJSON);
                return;
            }
            TUser tUser = JWTUtils.parseUserFromJWT(token);
            String redisToken = (String) redisService.getValue(Constants.REDIS_JWT_KEY + tUser.getId());
            if(!StringUtils.hasText(redisToken)){
//                没有获取到内容说明token过期了
                Result fail = Result.FAIL(CodeEnum.TOKEN_IS_EXPIRED);
                String json = JSONUtils.toJSON(fail);
                ResponseUtils.write(response,json);
                return;
            }
            if (!redisToken.equals(token)) {
//                登陆失败token错误
                Result result = Result.FAIL(CodeEnum.TOKEN_IS_ERROR);
//                把R对象转为JSON
                String json = JSONUtils.toJSON(result);
                ResponseUtils.write(response,json);
                return;
            }
//            jwt验证通过了
            UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(tUser,tUser.getLoginPwd(),tUser.getAuthorities());
            SecurityContextHolder.getContext().setAuthentication(authenticationToken);
//            刷新一下token
//            做异步执行
//            new Thread(new Runnable() {
//                @Override
//                public void run() {
                   这里刷新token即可
                   从请求头中获取
//                    String rememberMe = request.getHeader("rememberMe");
//                    if (!Boolean.parseBoolean(rememberMe)) {
//                        redisService.expire(Constants.REDIS_JWT_KEY + tUser.getId(), Constants.DEFAULT_EXPIRE_TIME, TimeUnit.SECONDS);
//                    }
//                }
//            }).start();
//            最好使用线程池的方式去执行
//            threadPoolTaskExecutor.execute(() -> {
//                    这里刷新token即可
//                    从请求头中获取
//                    String rememberMe = null;
//                    if(StringUtils.hasText(request.getHeader(Constants.REMEMBER_ME))){
//                        rememberMe = request.getHeader(Constants.REMEMBER_ME);
//                    }
//                    if (!Boolean.parseBoolean(rememberMe)) {
//                        redisService.expire(Constants.REDIS_JWT_KEY + tUser.getId(), Constants.DEFAULT_EXPIRE_TIME, TimeUnit.SECONDS);
//                    }
//            });
//            验证jwt通过了,让filter链继续执行


//            经过实验,线程池有概率导致请求和我们的service走的线程不是同一个导致请求头里面获取这个rememberMe报错
//            还是不用线程为好,慢点就慢点吧
            String rememberMe = null;
            if(StringUtils.hasText(request.getHeader(Constants.REMEMBER_ME))){
                rememberMe = request.getHeader(Constants.REMEMBER_ME);
            }
            if (!Boolean.parseBoolean(rememberMe)) {
                redisService.expire(Constants.REDIS_JWT_KEY + tUser.getId(), Constants.DEFAULT_EXPIRE_TIME, TimeUnit.SECONDS);
            }
            filterChain.doFilter(request,response);
        }
    }
}
 

package com.alatus.config.listener;

import com.alatus.mapper.TClueMapper;
import com.alatus.model.TClue;
import com.alatus.model.TUser;
import com.alatus.util.JSONUtils;
import com.alatus.util.JWTUtils;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.read.listener.ReadListener;
import com.alibaba.excel.util.ListUtils;
import lombok.extern.slf4j.Slf4j;

import java.util.Date;
import java.util.List;

/**
 * 每读一行Excel的数据,就会触发该监听器中的invoke()方法,Excel读完之后会触发该监听器中的doAfterAllAnalysed()方法
 */
@Slf4j
public class UploadDataListener implements ReadListener {

    /**
     * 每隔100条存储数据库,实际使用中可以100条,然后清理list ,方便内存回收
     */
    private static final int BATCH_COUNT = 100;

    //缓存List
    private List cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);

    /**
     * 假设这个是一个DAO,当然有业务逻辑这个也可以是一个service。当然如果不用存储这个对象没用。
     */
    private TClueMapper tClueMapper;

    private String token;

    /**
     * 如果使用了spring,请使用这个构造方法。每次创建Listener的时候需要把spring管理的类传进来
     *
     */
    public UploadDataListener(TClueMapper tClueMapper, String token) {
        this.tClueMapper = tClueMapper;
        this.token = token;
    }

    /**
     * 这个每一条数据解析都会来调用
     *
     */
    @Override
    public void invoke(TClue tClue, AnalysisContext context) {
        log.info("读取到的每一条数据:{}", JSONUtils.toJSON(tClue));
        //给读到的clue对象设置创建时间(导入时间)和创建人(导入人)
        tClue.setCreateTime(new Date());
        TUser tUser = JWTUtils.parseUserFromJWT(token);
        tClue.setCreateBy(tUser.getId());
        //每读取一行,就把该数据放入到一个缓存List中
        cachedDataList.add(tClue);
        // 达到BATCH_COUNT了,需要去存储一次数据库,防止数据几万条数据在内存,容易OOM
        if (cachedDataList.size() >= BATCH_COUNT) {
            //把缓存list中的数据写入到数据库
            saveData();

            //存储完成清空list
            cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);
        }
    }

    /**
     * 所有数据解析完成了 都会来调用
     *
     */
    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
        // 这里也要保存数据,确保最后遗留的数据也存储到数据库
        saveData();
        log.info("所有数据解析完成!");
    }

    /**
     * 加上存储数据库
     */
    private void saveData() {
        log.info("{}条数据,开始存储数据库!", cachedDataList.size());
        tClueMapper.saveClue(cachedDataList);
        log.info("存储数据库成功!");
    }
}

 

package com.alatus.config.listener;

import com.alatus.mapper.TClueMapper;
import com.alatus.model.TClue;
import com.alatus.model.TUser;
import com.alatus.util.JSONUtils;
import com.alatus.util.JWTUtils;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.read.listener.ReadListener;
import com.alibaba.excel.util.ListUtils;
import lombok.extern.slf4j.Slf4j;

import java.util.Date;
import java.util.List;

/**
 * 每读一行Excel的数据,就会触发该监听器中的invoke()方法,Excel读完之后会触发该监听器中的doAfterAllAnalysed()方法
 */
@Slf4j
public class UploadDataListener implements ReadListener {

    /**
     * 每隔100条存储数据库,实际使用中可以100条,然后清理list ,方便内存回收
     */
    private static final int BATCH_COUNT = 100;

    //缓存List
    private List cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);

    /**
     * 假设这个是一个DAO,当然有业务逻辑这个也可以是一个service。当然如果不用存储这个对象没用。
     */
    private TClueMapper tClueMapper;

    private String token;

    /**
     * 如果使用了spring,请使用这个构造方法。每次创建Listener的时候需要把spring管理的类传进来
     *
     */
    public UploadDataListener(TClueMapper tClueMapper, String token) {
        this.tClueMapper = tClueMapper;
        this.token = token;
    }

    /**
     * 这个每一条数据解析都会来调用
     *
     */
    @Override
    public void invoke(TClue tClue, AnalysisContext context) {
        log.info("读取到的每一条数据:{}", JSONUtils.toJSON(tClue));
        //给读到的clue对象设置创建时间(导入时间)和创建人(导入人)
        tClue.setCreateTime(new Date());
        TUser tUser = JWTUtils.parseUserFromJWT(token);
        tClue.setCreateBy(tUser.getId());
        //每读取一行,就把该数据放入到一个缓存List中
        cachedDataList.add(tClue);
        // 达到BATCH_COUNT了,需要去存储一次数据库,防止数据几万条数据在内存,容易OOM
        if (cachedDataList.size() >= BATCH_COUNT) {
            //把缓存list中的数据写入到数据库
            saveData();

            //存储完成清空list
            cachedDataList = ListUtils.newArrayListWithExpectedSize(BATCH_COUNT);
        }
    }

    /**
     * 所有数据解析完成了 都会来调用
     *
     */
    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
        // 这里也要保存数据,确保最后遗留的数据也存储到数据库
        saveData();
        log.info("所有数据解析完成!");
    }

    /**
     * 加上存储数据库
     */
    private void saveData() {
        log.info("{}条数据,开始存储数据库!", cachedDataList.size());
        tClueMapper.saveClue(cachedDataList);
        log.info("存储数据库成功!");
    }
}

package com.alatus.config;

import com.alatus.config.filter.TokenVerifyFilter;
import com.alatus.config.handler.MyAccessDeniedHandler;
import com.alatus.config.handler.MyAuthenticationFailureHandler;
import com.alatus.config.handler.MyAuthenticationSuccessHandler;
import com.alatus.config.handler.MyLogoutSuccessHandler;
import com.alatus.constant.Constants;
import jakarta.annotation.Resource;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.method.configuration.EnableMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.logout.LogoutFilter;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.CorsConfigurationSource;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
import java.util.Arrays;

//开启方法级别的权限检查
@EnableMethodSecurity
@Configuration
public class SecurityConfig {
    @Resource
    private MyAuthenticationSuccessHandler myAuthenticationSuccessHandler;
    @Resource
    private MyLogoutSuccessHandler myLogoutSuccessHandler;
    @Resource
    private TokenVerifyFilter tokenVerifyFilter;
//    权限不足
    @Resource
    private MyAccessDeniedHandler myAccessDeniedHandler;

//    配置加密器
    @Bean
    public PasswordEncoder passwordEncoder(){
        return new BCryptPasswordEncoder();
    }
    @Resource
    private MyAuthenticationFailureHandler myAuthenticationFailureHandler;
    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity httpSecurity,CorsConfigurationSource configurationSource) throws Exception{
        return httpSecurity
                .formLogin((formLogin) -> {
                    formLogin.loginProcessingUrl((Constants.LOGIN_URI))
                            .usernameParameter("loginAct")
                            .passwordParameter("loginPwd")
                            .successHandler(myAuthenticationSuccessHandler)
                            .failureHandler(myAuthenticationFailureHandler);
                })
//        SecurityFilterChain改变了默认行为,不再拦截了,需要手动拦截
                .authorizeHttpRequests((authorize) -> {
//                    对任何请求进行拦截,任何请求都需要登录才可以访问
//                    /api/login这个请求放开,其他请求正常拦截
                    authorize.requestMatchers(Constants.LOGIN_URI).permitAll().anyRequest().authenticated();
                })
                .csrf((csrf) -> {
                    //禁用跨站请求伪造
                    csrf.disable();
                })
                //支持跨域请求
                .cors((cors)->{
                    cors.configurationSource(configurationSource);
                })
                .sessionManagement((session) -> {
//                    让session的创建策略为不创建
                    session.sessionCreationPolicy(SessionCreationPolicy.STATELESS);
                })
//                添加我们自定义的filter
                .addFilterBefore(tokenVerifyFilter, LogoutFilter.class)
//                退出登录
                .logout((logout) -> {
//                    退出的地址,这个也不需要我们写controller
                    logout.logoutUrl("/api/logOut").logoutSuccessHandler(myLogoutSuccessHandler);
                })
                //无权限时的处理方法
                .exceptionHandling((exceptionHandling) -> {
                    exceptionHandling.accessDeniedHandler(myAccessDeniedHandler);
                })
                .build();
    }
    @Bean
    public CorsConfigurationSource configurationSource(){
        CorsConfiguration corsConfiguration = new CorsConfiguration();
        corsConfiguration.setAllowedOrigins(Arrays.asList("*"));//允许任意来源
        corsConfiguration.setAllowedMethods(Arrays.asList("*"));//允许任意方法请求
        corsConfiguration.setAllowedHeaders(Arrays.asList("*"));//允许请求头任意内容
        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
//        任何路径都按这个来
        source.registerCorsConfiguration("/**",corsConfiguration);
        return source;
    }
}

 

package com.alatus.config;

import com.alatus.config.filter.TokenVerifyFilter;
import com.alatus.config.handler.MyAccessDeniedHandler;
import com.alatus.config.handler.MyAuthenticationFailureHandler;
import com.alatus.config.handler.MyAuthenticationSuccessHandler;
import com.alatus.config.handler.MyLogoutSuccessHandler;
import com.alatus.constant.Constants;
import jakarta.annotation.Resource;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.method.configuration.EnableMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.logout.LogoutFilter;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.CorsConfigurationSource;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
import java.util.Arrays;

//开启方法级别的权限检查
@EnableMethodSecurity
@Configuration
public class SecurityConfig {
    @Resource
    private MyAuthenticationSuccessHandler myAuthenticationSuccessHandler;
    @Resource
    private MyLogoutSuccessHandler myLogoutSuccessHandler;
    @Resource
    private TokenVerifyFilter tokenVerifyFilter;
//    权限不足
    @Resource
    private MyAccessDeniedHandler myAccessDeniedHandler;

//    配置加密器
    @Bean
    public PasswordEncoder passwordEncoder(){
        return new BCryptPasswordEncoder();
    }
    @Resource
    private MyAuthenticationFailureHandler myAuthenticationFailureHandler;
    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity httpSecurity,CorsConfigurationSource configurationSource) throws Exception{
        return httpSecurity
                .formLogin((formLogin) -> {
                    formLogin.loginProcessingUrl((Constants.LOGIN_URI))
                            .usernameParameter("loginAct")
                            .passwordParameter("loginPwd")
                            .successHandler(myAuthenticationSuccessHandler)
                            .failureHandler(myAuthenticationFailureHandler);
                })
//        SecurityFilterChain改变了默认行为,不再拦截了,需要手动拦截
                .authorizeHttpRequests((authorize) -> {
//                    对任何请求进行拦截,任何请求都需要登录才可以访问
//                    /api/login这个请求放开,其他请求正常拦截
                    authorize.requestMatchers(Constants.LOGIN_URI).permitAll().anyRequest().authenticated();
                })
                .csrf((csrf) -> {
                    //禁用跨站请求伪造
                    csrf.disable();
                })
                //支持跨域请求
                .cors((cors)->{
                    cors.configurationSource(configurationSource);
                })
                .sessionManagement((session) -> {
//                    让session的创建策略为不创建
                    session.sessionCreationPolicy(SessionCreationPolicy.STATELESS);
                })
//                添加我们自定义的filter
                .addFilterBefore(tokenVerifyFilter, LogoutFilter.class)
//                退出登录
                .logout((logout) -> {
//                    退出的地址,这个也不需要我们写controller
                    logout.logoutUrl("/api/logOut").logoutSuccessHandler(myLogoutSuccessHandler);
                })
                //无权限时的处理方法
                .exceptionHandling((exceptionHandling) -> {
                    exceptionHandling.accessDeniedHandler(myAccessDeniedHandler);
                })
                .build();
    }
    @Bean
    public CorsConfigurationSource configurationSource(){
        CorsConfiguration corsConfiguration = new CorsConfiguration();
        corsConfiguration.setAllowedOrigins(Arrays.asList("*"));//允许任意来源
        corsConfiguration.setAllowedMethods(Arrays.asList("*"));//允许任意方法请求
        corsConfiguration.setAllowedHeaders(Arrays.asList("*"));//允许请求头任意内容
        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
//        任何路径都按这个来
        source.registerCorsConfiguration("/**",corsConfiguration);
        return source;
    }
}
 

package com.alatus.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;

@Configuration
public class RedisConfig
{
    @Bean
    public RedisTemplate redisTemplate(LettuceConnectionFactory lettuceConnectionFactory){
        RedisTemplate redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(lettuceConnectionFactory);
        redisTemplate.setKeySerializer(new StringRedisSerializer());
        redisTemplate.setValueSerializer(new GenericJackson2JsonRedisSerializer());
        redisTemplate.setHashKeySerializer(new StringRedisSerializer());
        redisTemplate.setHashValueSerializer(new GenericJackson2JsonRedisSerializer());
        redisTemplate.afterPropertiesSet();
        return redisTemplate;
    }
}

 

package com.alatus.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;

@Configuration
public class RedisConfig
{
    @Bean
    public RedisTemplate redisTemplate(LettuceConnectionFactory lettuceConnectionFactory){
        RedisTemplate redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(lettuceConnectionFactory);
        redisTemplate.setKeySerializer(new StringRedisSerializer());
        redisTemplate.setValueSerializer(new GenericJackson2JsonRedisSerializer());
        redisTemplate.setHashKeySerializer(new StringRedisSerializer());
        redisTemplate.setHashValueSerializer(new GenericJackson2JsonRedisSerializer());
        redisTemplate.afterPropertiesSet();
        return redisTemplate;
    }
}

你可能感兴趣的:(CRM项目,#,Spring-Boot框架,#,Spring框架,mybatis,分布式,后端,spring,cloud,微服务,java,spring,boot)