首页 > 其他分享 >springsecurity6学习

springsecurity6学习

时间:2024-08-28 14:47:26浏览次数:11  
标签:return String 学习 static org import springsecurity6 public

1、maven依赖

<properties>
        <maven.compiler.source>17</maven.compiler.source>
        <maven.compiler.target>17</maven.compiler.target>
        <spring.version>3.2.0</spring.version>
        <commons.version>3.12.0</commons.version>
        <codec.version>1.15</codec.version>
    </properties>

    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-dependencies</artifactId>
                <version>${spring.version}</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
            <dependency>
                <groupId>org.apache.commons</groupId>
                <artifactId>commons-lang3</artifactId>
                <version>${commons.version}</version>
            </dependency>
            <dependency>
                <groupId>commons-codec</groupId>
                <artifactId>commons-codec</artifactId>
                <version>${codec.version}</version>
            </dependency>
            <dependency>
                <groupId>org.mybatis.spring.boot</groupId>
                <artifactId>mybatis-spring-boot-starter</artifactId>
                <version>3.0.3</version>
            </dependency>
            <dependency>
                <groupId>mysql</groupId>
                <artifactId>mysql-connector-java</artifactId>
                <version>8.0.18</version>
                <scope>runtime</scope>
            </dependency>
            <dependency>
                <groupId>org.projectlombok</groupId>
                <artifactId>lombok</artifactId>
                <version>1.18.32</version>
                <scope>provided</scope>
            </dependency>
            <dependency>
                <groupId>com.alibaba</groupId>
                <artifactId>fastjson</artifactId>
                <version>1.2.83</version>
            </dependency>
            <dependency>
                <groupId>com.auth0</groupId>
                <artifactId>java-jwt</artifactId>
                <version>4.4.0</version>
            </dependency>
            <dependency>
                <groupId>com.fasterxml.jackson.core</groupId>
                <artifactId>jackson-annotations</artifactId>
                <version>2.15.2</version>
            </dependency>
            <dependency>
                <groupId>com.fasterxml.jackson.core</groupId>
                <artifactId>jackson-core</artifactId>
                <version>2.15.2</version>
            </dependency>
            <dependency>
                <groupId>com.fasterxml.jackson.core</groupId>
                <artifactId>jackson-databind</artifactId>
                <version>2.15.2</version>
            </dependency>
        </dependencies>
    </dependencyManagement>

    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <configuration>
                    <source>16</source>
                    <target>16</target>
                </configuration>
            </plugin>
        </plugins>
    </build>

  

2、config配置

a.CorsConfig.java

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

/**
 * @author Administrator
 */
@Configuration
public class CorsConfig implements WebMvcConfigurer {
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("/**")
                // 是否发送cookie
                .allowCredentials(true)
                .allowedOriginPatterns("*")
                .allowedMethods(new String[]{"GET","POST","PUT","DELETE"})
                .allowedHeaders("*")
                .exposedHeaders("*");
    }
}

  

b.SecurityConfig.java

import jakarta.servlet.http.Cookie;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.pro.filter.JwtAuthenticationTokenFilter;
import org.pro.filter.LoginFilter;
import org.pro.model.Resource;
import org.pro.service.ResourceService;
import org.pro.service.UserService;
import org.pro.utils.EncryptionUtils;
import org.pro.utils.JwtUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.configuration.AuthenticationConfiguration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.AuthenticationFailureHandler;
import org.springframework.security.web.authentication.AuthenticationSuccessHandler;
import org.springframework.security.web.authentication.RememberMeServices;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.security.web.authentication.rememberme.TokenBasedRememberMeServices;
import org.springframework.util.CollectionUtils;

import java.util.List;

/**
 * @author Administrator
 */
@Configuration
@EnableWebSecurity
@Slf4j
public class SecurityConfig {
    private ResourceService resourceService;
    private UserService userService;
    private AuthenticationConfiguration authenticationConfiguration;

    /**
     * 认证链
     * @param http
     * @return
     * @throws Exception
     */
    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        List<Resource> resources = this.resourceService.getAllResources();
        if (!CollectionUtils.isEmpty(resources) && resources.size()>0) {
            http.authorizeHttpRequests(auth -> {
                for (Resource resource : resources) {
                    String authorityCode = resource.getAuthorityCode();
                    if (StringUtils.isNotBlank(authorityCode)) {
                        auth.requestMatchers(resource.getUrl()).hasAuthority(authorityCode);
                    } else {
                        auth.requestMatchers(resource.getUrl()).permitAll();
                    }
                }
                auth.anyRequest().authenticated();
            });
        }

        // 登录
        // loginPage:登录页面url
        // loginProcessingUrl:登录表单提交url
        http.formLogin(formLogin -> formLogin.loginProcessingUrl("/login"));
        // 登陆之前获取并校验token
        http.addFilterBefore(new JwtAuthenticationTokenFilter(), UsernamePasswordAuthenticationFilter.class);

        // 自定义登录过滤器,使用addFilterAt时,权限出错,可能原因是过滤器位置的问题
        http.addFilterAt(loginFilter(), UsernamePasswordAuthenticationFilter.class);
        // 前后端分离时,使用addFilterAfter会返回一个登录的html页面代码
        // http.addFilterAfter(loginFilter(), UsernamePasswordAuthenticationFilter.class);

        http.csrf(csrf -> csrf.disable());
        // cors跨域关闭
        // http.cors(cors -> cors.disable());
        // 前后端未分离使用
        // http.rememberMe(rememberMe -> rememberMe.rememberMeParameter("rememberMe").rememberMeCookieName("rememberMe"));

        //http.logout(login -> login.logoutUrl("/logout"));

        //http.exceptionHandling(e -> e.accessDeniedPage("/login/error"));
        return http.build();
    }

    @Bean
    public UserDetailsService userDetailsService() {
        return loginName -> {
            org.pro.model.User user = this.userService.getUserByName(loginName);
            if (user == null) {
                throw new UsernameNotFoundException("用户未找到");
            }
            List<String> codes = user.getCodes();
            String[] authCodeArr = new String[codes.size()];
            return User.withUsername(loginName).password(user.getPassword()).authorities(codes.toArray(authCodeArr)).build();
        };
    }

    @Bean
    public RememberMeServices rememberMeServices(UserDetailsService userDetailsService) {
        TokenBasedRememberMeServices.RememberMeTokenAlgorithm encodingAlgorithm = TokenBasedRememberMeServices.RememberMeTokenAlgorithm.SHA256;
        TokenBasedRememberMeServices rememberMe = new TokenBasedRememberMeServices("myKey", userDetailsService, encodingAlgorithm);
        rememberMe.setMatchingAlgorithm(TokenBasedRememberMeServices.RememberMeTokenAlgorithm.MD5);
        return rememberMe;
    }

    /**
     * 启动注入会调用
     * @return
     * @throws Exception
     */
    @Bean
    public LoginFilter loginFilter() throws Exception {
        LoginFilter loginFilter = new LoginFilter();
        loginFilter.setAuthenticationManager(authenticationConfiguration.getAuthenticationManager());
        loginFilter.setAuthenticationSuccessHandler(authenticationSuccessHandler());
        loginFilter.setAuthenticationFailureHandler(authenticationFailureHandler());
        return loginFilter;
    }

    @Bean
    public AuthenticationSuccessHandler authenticationSuccessHandler() {
        return (HttpServletRequest request, HttpServletResponse response, Authentication authentication) -> {
            System.out.println("==========登录校验成功==========");
            // response.sendRedirect("/index");
            /*response.setContentType("application/json;charset=UTF-8");
            response.getWriter().write("==========登陆成功==========");*/
            // 结果为""
            // System.out.println("getContextPath:"+request.getContextPath());
            // 结果为/login
            // System.out.println("getRequestURI:"+request.getRequestURI());
            // 结果为/login
            // System.out.println("getServletPath:"+request.getServletPath());
            // 结果为http://localhost:8081/login
            // System.out.println("getRequestURL:"+request.getRequestURL());
            // response.sendRedirect(request.getRequestURI());
            Cookie cookie = new Cookie("rememberMe", JwtUtils.genToken(authentication));
            cookie.setAttribute("test", "test");
            response.addCookie(cookie);
            response.setContentType("application/json;charset=UTF-8");
            response.getWriter().write("登录成功");
        };
    }

    @Bean
    public AuthenticationFailureHandler authenticationFailureHandler() {
        return (HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) -> {
            System.out.println("==========登录校验失败==========");
            exception.printStackTrace();
        };
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        return new PasswordEncoder() {
            @Override
            public String encode(CharSequence rawPassword) {
                if (rawPassword == null) {
                    throw new IllegalArgumentException("rawPassword cannot be null");
                }
                return EncryptionUtils.sha256(rawPassword.toString());
            }

            @Override
            public boolean matches(CharSequence rawPassword, String encodedPassword) {
                if (encodedPassword == null || encodedPassword.length() == 0) {
                    log.info("Empty encoded password");
                    return false;
                }
                return encode(rawPassword).equals(encodedPassword);
            }
        };
    }

    @Autowired
    public void setResourceService(ResourceService resourceService) {
        this.resourceService = resourceService;
    }

    @Autowired
    public void setUserService(UserService userService) {
        this.userService = userService;
    }

    @Autowired
    public void setAuthenticationConfiguration(AuthenticationConfiguration authenticationConfiguration) {
        this.authenticationConfiguration = authenticationConfiguration;
    }
}

  

3、filter过滤器

a.JwtAuthenticationTokenFilter.java

import jakarta.servlet.FilterChain;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.Cookie;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.pro.utils.JwtUtils;
import org.springframework.web.filter.OncePerRequestFilter;

import java.io.IOException;

/**
 * @author Administrator
 */
public class JwtAuthenticationTokenFilter extends OncePerRequestFilter {
    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {
        String name = "rememberMe";
        Cookie[] cookies = request.getCookies();
        if (cookies != null) {
            for (Cookie cookie : cookies) {
                if (name.equals(cookie.getName())) {
                    System.out.println("已获取到token");
                    try {
                        JwtUtils.tokenVerify(cookie.getValue());
                    } catch (Exception e) {
                        response.setContentType("text/html;charset=UTF-8");
                        response.getWriter().write("非法token");
                        return;
                    }
                }
            }
        }
        filterChain.doFilter(request, response);
    }
}

  

b.LoginFilter.java

import com.alibaba.fastjson.JSON;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.SneakyThrows;
import org.apache.commons.lang3.StringUtils;
import org.pro.model.User;
import org.springframework.security.authentication.AuthenticationServiceException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;

import java.io.BufferedReader;
import java.io.IOException;
import java.util.Map;

/**
 * @author Administrator
 */
public class LoginFilter extends UsernamePasswordAuthenticationFilter {
    private final String method = "POST";

    @SneakyThrows
    @Override
    public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
        if (! method.equals(request.getMethod()) ) {
            throw new AuthenticationServiceException("请求方法错误,请求方法应为POST,当前请求方法是:" + request.getMethod());
        }
        User user = obtainUser(request);
        UsernamePasswordAuthenticationToken authentication = UsernamePasswordAuthenticationToken.unauthenticated(user.getLoginName(), user.getPassword());

        // 此处可能报错,AuthenticationManager可能为空
        return this.getAuthenticationManager().authenticate(authentication);
    }

    private User obtainUser(HttpServletRequest request) throws IOException {
        User user = new User();
        String username = request.getParameter("username");
        String password = request.getParameter("password");
        if (StringUtils.isBlank(username) || StringUtils.isBlank(password)) {
            BufferedReader reader = request.getReader();
            StringBuffer sb = new StringBuffer();
            String line = null;
            if ((line = reader.readLine()) != null) {
                sb.append(line);
            }
            reader.close();
            Map<String, String> map = JSON.parseObject(sb.toString(), Map.class);
            username = map.get("username");
            password = map.get("password");
            if (StringUtils.isBlank(username) || StringUtils.isBlank(password)) {
                throw new AuthenticationServiceException("用户或密码为空");
            }
        }
        user.setLoginName(username);
        user.setPassword(password);
        return user;
    }

}

  

4、工具类

a.AESUtils.java

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.crypto.Cipher;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
import java.security.Key;
import java.util.Base64;

/**
 * @author Administrator
 */
public class AESUtils {

    static Logger logger = LoggerFactory.getLogger(AESUtils.class);

    /**
     * 密钥
     */
    public static String key = "1A2B3C4D5E6F7G8h";

    /**
     * 密钥算法
     */
    public static final String KEY_ALGORITHM = "AES";

    /**
     * 加密/解密算法 / 工作模式 / 填充方式
     */
    public static final String CIPHER_ALGORITHM = "AES/ECB/PKCS5Padding";

    private static final Base64.Decoder DECODE_64 = Base64.getDecoder();
    private static final Base64.Encoder ENCODE_64 = Base64.getEncoder();
    private static final String CHARSET = "utf-8";

    /**
     * 转换密钥
     * @param key 二进制密钥
     * @return Key 密钥
     * @throws Exception
     */
    private static Key toKey(byte[] key) {

        // 实例化AES密钥材料
        SecretKey secretKey = new SecretKeySpec(key, KEY_ALGORITHM);

        return secretKey;
    }
    /**
     * 解密
     * @param content 待解密数据
     * @return byte[] 解密数据
     * @throws Exception
     */
    public static String decrypt(String content) throws Exception {

        // 还原密钥
        Key k = toKey(key.getBytes(CHARSET));

        byte[] data = content.getBytes(CHARSET);

        // PKCS5Padding实例化,使用PKCS7Padding填充方式是Cipher.getInstance(CIPHER_ALGORITHM, "BC")
        Cipher cipher = Cipher.getInstance(CIPHER_ALGORITHM);

        // 初始化,设置为解密模式
        cipher.init(Cipher.DECRYPT_MODE, k);

        // 执行操作
        return new String(cipher.doFinal(DECODE_64.decode(data)));
    }

    /**
     * 加密
     * @param content 待加密数据
     * @return byte[] 加密数据
     * @throws Exception
     */
    public static String encrypt(String content) throws Exception {

        // 还原密钥
        Key k = toKey(key.getBytes(StandardCharsets.UTF_8));

        byte[] data = content.getBytes(CHARSET);

        // PKCS5Padding实例化,使用PKCS7Padding填充方式是Cipher.getInstance(CIPHER_ALGORITHM, "BC")
        Cipher cipher = Cipher.getInstance(CIPHER_ALGORITHM);

        // 初始化,设置为加密模式
        cipher.init(Cipher.ENCRYPT_MODE, k);

        // 执行操作
        return ENCODE_64.encodeToString(cipher.doFinal(data));
    }

}

  

b.CommonUtils.java

import jakarta.servlet.http.HttpServletRequest;
import org.apache.commons.lang3.StringUtils;
import org.springframework.cglib.beans.BeanMap;

import java.beans.BeanInfo;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.lang.reflect.Field;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.regex.Pattern;

/**
 * @author Administrator
 */
public class CommonUtils {

    private static final Map<String, Object> map = new HashMap<String, Object>();
    private static final String DATE_FORMAT = "yyyy-MM-dd'T'HH:mm";

    /**
     * 2019年10月4日16:56:58 隐藏身份证后六位
     *
     * @param identityCard
     * @return
     */
    public static String hidIdentityCard(String identityCard) {
        // 增加身份证校验
        String pattern = "(^\\d{15}$)|(^\\d{18}$)|(^\\d{17}(\\d|X|x)$)";
        if (StringUtils.isNotBlank(identityCard)) {
            if (Pattern.compile(pattern).matcher(identityCard).matches()) {
                return identityCard.substring(0, identityCard.length() - 6) + "xxxxxx";
            } else {
                throw new CustomException("身份证校验失败");
            }
        } else {
            throw new NullPointerException("身份证不能为空");
        }
    }

    public static Map<String, String> switchMapToString(HttpServletRequest request) {
        Map<String, String[]> paramMap = request.getParameterMap();
        Map<String, String> switchMap = new HashMap<>();
        if (paramMap.isEmpty()) {
            return switchMap;
        }
        for (Map.Entry<String, String[]> entry : paramMap.entrySet()) {
            String key = entry.getKey();
            String value = entry.getValue()[0];
            if (StringUtils.isNotBlank(key) && StringUtils.isNotBlank(value)) {
                switchMap.put(entry.getKey(), entry.getValue()[0]);
            }
        }
        return switchMap;
    }

    public static Map<String, Object> switchMapToObject(HttpServletRequest request) {
        Map<String, String[]> paramMap = request.getParameterMap();
        Map<String, Object> switchMap = new HashMap<>();
        if (paramMap.isEmpty()) {
            return switchMap;
        }
        for (Map.Entry<String, String[]> entry : paramMap.entrySet()) {
            String key = entry.getKey();
            String value = entry.getValue()[0];
            if (StringUtils.isNotBlank(key) && StringUtils.isNotBlank(value)) {
                switchMap.put(entry.getKey(), request.getParameter(key));
            }
        }
        return switchMap;
    }

    /**
     * admin:构建一个干净的map,不需要每次都new一个新的
     *
     * @return
     */
    public static Map<String, Object> getClearMap() {
        if (!map.isEmpty()) {
            map.clear();
        }
        return map;
    }

    /**
     * 按分隔符将字符串转成集合,此几个不可增删
     *
     * @param str
     * @param separator
     * @return
     */
    public static List<String> splitStrBySeparator(String str, String separator) {
        if (StringUtils.isBlank(str)) {
            throw new NullPointerException("切割的字符串不能为空!");
        }
        if (StringUtils.isBlank(separator)) {
            separator = ",";
        }
        return Arrays.asList(str.split(separator));
    }

    public static List<Long> splitStrToLongBySeparator(String str, String separator) {
        List<Long> longList = new ArrayList<>();
        List<String> stringList = splitStrBySeparator(str, separator);
        stringList.forEach(string -> {
            longList.add(Long.parseLong(string));
        });
        return longList;
    }

    public static String[] listToArray(List<String> stringList) {
        String[] stringArray = new String[stringList.size()];
        for (int i = 0; i < stringList.size(); i++) {
            stringArray[i] = stringList.get(i);
        }
        return stringArray;
    }

    /**
     * 通过反射将javaBean对象转成Map
     *
     * @param obj -->javaBean
     * @param nullFlag -->空值是否添加到map中
     * @return 返回key为属性名,value为属性值的map
     */
    public static Map<String, Object> objToMap(Object obj, boolean nullFlag) {
        Map<String, Object> map = new HashMap<>(16);
        try {
            Class<?> clazz = obj.getClass();
            for (Field field : clazz.getDeclaredFields()) {
                field.setAccessible(true);
                Object value = field.get(obj);
                if (nullFlag && value == null) {
                    String fieldName = field.getName();
                    map.put(fieldName, value);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return map;
    }

    public static <T> T mapToBean(T bean, Map<String, Object> map) {
        BeanMap beanMap = BeanMap.create(bean);
        beanMap.putAll(map);
        return bean;
    }

    public static <T> T mapToBean(Map<String, Object> map, Class<T> beanType) throws Exception {
        // 创建javaBean对象
        Object obj = beanType.newInstance();
        BeanInfo beanInfo = Introspector.getBeanInfo(beanType, Object.class);
        PropertyDescriptor[] pds = beanInfo.getPropertyDescriptors();
        for (PropertyDescriptor pd : pds) {
            // 从Map中获取属性同名的key值
            Object value = map.get(pd.getName());
            // 调用setter方法设置属性值
            pd.getWriteMethod().invoke(obj, value);
        }
        return (T)obj;
    }

    public static String getIPAddress(HttpServletRequest request) {
        String ip = request.getHeader("X-Forwarded-For");
        String unknown = "unknown";
        if (ip == null || ip.length() == 0 || unknown.equalsIgnoreCase(ip)) {
            ip = request.getHeader("Proxy-Client-IP");
        }
        if (ip == null || ip.length() == 0 || unknown.equalsIgnoreCase(ip)) {
            ip = request.getHeader("WL-Proxy-Client-IP");
        }
        if (ip == null || ip.length() == 0 || unknown.equalsIgnoreCase(ip)) {
            ip = request.getHeader("HTTP_CLIENT_IP");
        }
        if (ip == null || ip.length() == 0 || unknown.equalsIgnoreCase(ip)) {
            ip = request.getHeader("HTTP_X_FORWARDED_FOR");
        }
        if (ip == null || ip.length() == 0 || unknown.equalsIgnoreCase(ip)) {
            ip = request.getRemoteAddr();
        }
        return ip;
    }

    public static Date getDate(String date) {
        if (StringUtils.isBlank(date)) {
            throw new CustomException("时间转换的时间字符串不能为空");
        }
        try {
            SimpleDateFormat sdf = new SimpleDateFormat(DATE_FORMAT);
            Date parse = sdf.parse(date);
            return parse;
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

}

  

c.CustomException.java

/**
 * @author Administrator
 */
public class CustomException extends RuntimeException {

    public CustomException() {}

    public CustomException(String message) {
        // 把参数传递给Throwable的带String参数的构造方法
        super(message);
    }

}

  

d.EncryptionUtils.java

import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;

import java.security.MessageDigest;

/**
 * @author Administrator
 */
@Slf4j
public class EncryptionUtils {

    private static final String SALT_VALUE = "hash_algorithm";
    private static final String ENCRYPTION_SHA256 = "SHA-256";
    private static final String ENCRYPTION_MD5 = "MD5";
    private static final String DEFAULT_ID_PREFIX = "{";
    private static final String DEFAULT_ID_SUFFIX = "}";

    /**
     * SHA-2加密,安全性高于SHA-1,sha256和sha512都属于SHA-2
     * @param input
     * @return
     */
    public static String sha256(String input) {
        try {
            if (StringUtils.isBlank(input)) {
                log.info("**********输入不能为空**********");
                throw new NullPointerException("输入不能为空");
            }
            // 添加盐值
            input = input + SALT_VALUE;
            MessageDigest digest = MessageDigest.getInstance("SHA-256");
            digest.update(input.getBytes());
            byte[] md = digest.digest();
            StringBuilder sb = new StringBuilder();
            for (byte b : md) {
                sb.append(String.format("%02x", b));
            }
            return DEFAULT_ID_PREFIX + "SHA-256" + DEFAULT_ID_SUFFIX + sb.toString();
        } catch (Exception e) {
            System.out.println("**********sha256加密报错**********");
            e.printStackTrace();
        }
        return null;
    }

    public static String md5(String input) {
        try {
            if (StringUtils.isBlank(input)) {
                log.info("**********输入不能为空**********");
                throw new NullPointerException("输入不能为空");
            }
            // 添加盐值
            input = input + SALT_VALUE;
            MessageDigest digest = MessageDigest.getInstance("MD5");
            digest.update(input.getBytes());
            byte[] md = digest.digest();
            StringBuilder sb = new StringBuilder();
            for (byte b : md) {
                sb.append(String.format("%02x", b));
            }
            return DEFAULT_ID_PREFIX + "MD5" + DEFAULT_ID_SUFFIX + sb.toString();
        } catch (Exception e) {
            System.out.println("**********md5加密报错**********");
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 当前只有sha256和md5加密
     * @param input
     * @param type
     * @return
     */
    public static String encryption(String input, String type) {
        try {
            if(StringUtils.isBlank(input)) {
                log.info("**********输入不能为空**********");
                throw new NullPointerException("输入不能为空");
            }
            if (StringUtils.isBlank(type) || !ENCRYPTION_SHA256.equals(type) || !ENCRYPTION_MD5.equals(type)) {
                type = ENCRYPTION_SHA256;
            }
            // 添加盐值
            input = input + SALT_VALUE;
            MessageDigest digest = MessageDigest.getInstance(type);
            digest.update(input.getBytes());
            byte[] md = digest.digest();
            StringBuilder sb = new StringBuilder();
            for (byte b : md) {
                sb.append(String.format("%02x", b));
            }
            return sb.toString();
        } catch (Exception e) {
            System.out.println("**********"+type+"加密报错**********");
            e.printStackTrace();
        }
        return null;
    }

}

  

e.JwtAuthentication.java

import org.springframework.security.core.Authentication;
import org.springframework.security.core.authority.SimpleGrantedAuthority;

import java.util.Collection;

/**
 * @author Administrator
 */
public class JwtAuthentication implements Authentication {

    private Collection<SimpleGrantedAuthority> authorities;
    private Object details;
    private boolean authenticated;
    private Object principal;
    private Object credentials;

    @Override
    public Collection<SimpleGrantedAuthority> getAuthorities() {
        return authorities;
    }

    public void setAuthorities(Collection<SimpleGrantedAuthority> authorities) {
        this.authorities = authorities;
    }

    @Override
    public Object getDetails() {
        return details;
    }

    public void setDetails(Object details) {
        this.details = details;
    }

    @Override
    public boolean isAuthenticated() {
        return authenticated;
    }

    @Override
    public void setAuthenticated(boolean authenticated) {
        this.authenticated = authenticated;
    }

    @Override
    public Object getPrincipal() {
        return principal;
    }

    public void setPrincipal(Object principal) {
        this.principal = principal;
    }

    @Override
    public Object getCredentials() {
        return credentials;
    }

    public void setCredentials(Object credentials) {
        this.credentials = credentials;
    }

    @Override
    public String getName() {
        return null;
    }
}

  

f.JwtUtils.java

import com.alibaba.fastjson.JSON;
import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTCreator;
import com.auth0.jwt.JWTVerifier;
import com.auth0.jwt.algorithms.Algorithm;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.User;

import java.util.Date;
import java.util.Map;

/**
 * @author Administrator
 */
@Slf4j
public class JwtUtils {

    private static final String secret = "project";
    // 30天
    private static final Long EXP_TIME = 1000L*60*60*24*30;

    /**
     * 根据验证和时间生成token
     * @param authentication 验证对象
     * @param expTime 过期时间
     * @return
     */
    public static String genToken(Authentication authentication, Long expTime) {
        if (expTime == null) {
            expTime = EXP_TIME;
        }
        Date expDate = new Date(System.currentTimeMillis()+expTime);

        User user = (User)authentication.getPrincipal();

        String userJson = JSON.toJSONString(user);

        String subject = "jwtToken";
        String authenticationJson = JSON.toJSONString(authentication);
        System.out.println("authenticationJson:"+authenticationJson);
        return JWT.create()
                .withSubject("token")
                // 配置过期时间
                .withExpiresAt(expDate)
                .withSubject(subject)
                // 设置接收方信息,登录用户信息
                .withClaim("user", userJson)
                .withAudience(authenticationJson)
                // 签证信息
                .sign(Algorithm.HMAC256(secret));
    }

    /**
     * 生成JWT token
     * @param authentication
     * @return
     */
    public static String genToken(Authentication authentication) {
        return genToken(authentication, EXP_TIME);
    }

    /**
     * 根据map差UN关键token
     * @param map 需要创建token的信息,保存在withClaim中
     * @param expTime 过期时间
     * @return
     */
    public static String genToken(Map<String, String> map, Long expTime) {
        if (expTime == null) {
            expTime = EXP_TIME;
        }
        JWTCreator.Builder builder = JWT.create();
        // 设置过期时间
        builder.withExpiresAt(new Date(System.currentTimeMillis()+expTime));
        map.forEach((key, value) -> {
            if (StringUtils.isNotBlank(key) && StringUtils.isNotBlank(value)) {
                builder.withClaim(key, value);
            }
        });
        return builder.sign(Algorithm.HMAC256(secret));
    }

    public static String genToken(Map<String, String> map) {
        return genToken(map, EXP_TIME);
    }

    public static void tokenVerify(String token) {
        try {
            JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256(secret)).build();
            jwtVerifier.verify(token);
            Date expiresAt = JWT.decode(token).getExpiresAt();
            // 判断时间是否过期
            if (!expiresAt.after(new Date())) {
                log.info("==========token已过期==========");
            }
            String json = JWT.decode(token).getAudience().get(0);
            JwtAuthentication authentication = JSON.parseObject(json, JwtAuthentication.class);
            log.info("===============token解析的对象:"+authentication);
            SecurityContextHolder.getContext().setAuthentication(authentication);
            log.info("==========token校验结束==========");
        } catch (Exception e) {
            e.printStackTrace();
            log.info("token校验失败");
        }
    }

}

  

标签:return,String,学习,static,org,import,springsecurity6,public
From: https://www.cnblogs.com/lizhenfeng/p/18384661

相关文章

  • 【学习笔记】SSL证书之文件格式
    SSL证书及密钥以文件的形式存在于我们的电脑上,这些文件一般为以下4种格式:DERPEMPFX/PKCS#12PKCS#71、DERDistinguishedEncodingRules(可辨别编码规则)是在线证书的格式二进制编码,如果用TXT进行查看会呈现出乱码。在SSL证书领域,我们一般不用DER格式的文件来交换证书(因为DER......
  • Qt/QML学习-Drawer
    QML学习Drawer例程视频讲解代码main.qmlimportQtQuick2.15importQtQuick.Window2.15importQtQuick.Controls2.15Window{width:640height:480visible:truetitle:qsTr("Drawer")Drawer{id:drawerwidth:pare......
  • 机器学习之——决策树信息熵计算[附加计算程序]
    0前言本文主要讲述了决策树背后的信息熵的公式含义及计算方式,并列举出多道例题帮助理解。1信息熵的定义1.1信息熵公式笔者使用下图(1-1)直观理解信息熵的含义。信息熵越大,表示该随机变量的不确定性越高。对于均匀分布,信息熵达到最大值。1.2证明:对于均匀分布,信息熵最......
  • 数据结构学习第一周
    本文需要掌握的知识1.认识数据结构2.了解数据结构(逻辑结构)的分类3.内存储器模型以及分配方式(物理结构)4.认识Node类5.简单了解泛型1.数据结构(D-S/DataStructure)1.1简介1.1.1数据分为原子数据和复合数据1.1.2结构分为逻辑结构和物理结构数据结构是由数据和数据......
  • STM32学习记录-08-USART串口
    1通信接口        通信的目的:将一个设备的数据传送到另一个设备,扩展硬件系统        通信协议:制定通信的规则,通信双方按照协议规则进行数据收发                USART:TX数据发送、RX数据接收        I2C:SCL时钟、SDA数据  ......
  • Cloud Studio:颠覆传统的云端开发与学习解决方案
    CloudStudioCloudStudio(云端IDE)是一款基于浏览器的集成开发环境,它为开发者提供了一个高效、稳定的云端工作站。用户在使用CloudStudio时,无需进行任何本地安装,只需通过浏览器即可随时随地轻松访问和使用。这种无缝的访问方式不仅提升了工作效率,也极大地简化了开发流程,使得开......
  • 学习笔记:基础动态规划
    线性DP定义具有线性“阶段”划分的动态规划算法被统称为线性动态规划入门线性动态DPLIS问题最长上升子序列问题。问题:给定一个长度为\(N\)的数列\(A\),求数值单调递增的子序列的长度最长是多少(子序列不需要连续)。经典的线性动态规划问题。分析:容易发现,对于某一个位......
  • Day09_0.1基础学习MATLAB学习小技巧总结(9)——数组运算
    利用空闲时间把碎片化的MATLAB知识重新系统的学习一遍,为了在这个过程中加深印象,也为了能够有所足迹,我会把自己的学习总结发在专栏中,以便学习交流。素材来源“数学建模清风”特此说明:本博客的内容只在于总结在使用matlab中的一些小技巧,并非教程,若想系统的学习MATLAB,也可以移步......
  • Day07_0.1基础学习MATLAB学习小技巧总结(7)——矩阵算数运算
    利用暑假的时间把碎片化的MATLAB知识重新系统的学习一遍,为了在这个过程中加深印象,也为了能够有所足迹,我会把自己的学习总结发在专栏中,以便学习交流。素材来源“数学建模清风”特此说明:本博客的内容只在于总结在使用matlab中的一些小技巧,并非教程,若想系统的学习MATLAB,也可以移......
  • 初步学习async/await,Task.GetAwaiter,Task.Result
    初步学习async/await,Task.GetAwaiter,Task.Result   网上关于async/await的知识有很多,看了很多但不如自己实践一遍来得快,所以这里记录下我的理解和大家学习下。  首先以最简单的同步方法来开始如下privatestaticvoidTest(){Console.Wr......