参考:https://www.jianshu.com/p/e88d3f8151d
一、 流程图
二、 具体实现
说明: 基于SpringBoot
- 引用依赖
<dependency>
|
- 关键编码
private UsersDTO getToken(UsersDTO user, Boolean isApp) { |
UserToken中设置用户信息传入JWT.sign方法返回加密后的token字符串,传入用户之后,便于后续反编译之后获取用户信息
JWT.sign(ut,timeout)
package com.yxg.jwt; import com.auth0.jwt.JWTSigner; import com.auth0.jwt.JWTVerifier; import com.auth0.jwt.internal.com.fasterxml.jackson.databind.ObjectMapper; import java.util.HashMap; import java.util.Map; public class JWT { private static final String SECRET = "123456"; private static final String EXP = "exp"; private static final String PAYLOAD = "payload"; /** 加密 * get jwt String of object * @param object * the POJO object * @param maxAge * the milliseconds of life time * @return the jwt token */ public static <T> String sign(T object, long maxAge) { try { final JWTSigner signer = new JWTSigner(SECRET); final Map<String, Object> claims = new HashMap<String, Object>(); ObjectMapper mapper = new ObjectMapper(); String jsonString = mapper.writeValueAsString(object); //存放有效信息 claims.put(PAYLOAD, jsonString); //设置过期时间 claims.put(EXP, System.currentTimeMillis() + maxAge); return signer.sign(claims); } catch(Exception e) { return null; } } /** 解密 * get the object of jwt if not expired * @param jwt * @return POJO object */ public static<T> T unsign(String jwt, Class<T> classT) { final JWTVerifier verifier = new JWTVerifier(SECRET); try { final Map<String,Object> claims= verifier.verify(jwt); if (claims.containsKey(EXP) && claims.containsKey(PAYLOAD)) { long exp = (Long)claims.get(EXP); long currentTimeMillis = System.currentTimeMillis(); if (exp > currentTimeMillis) { String json = (String)claims.get(PAYLOAD); ObjectMapper objectMapper = new ObjectMapper(); return objectMapper.readValue(json, classT); } } return null; } catch (Exception e) { return null; } } } |
3. 返回token示例
eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE2Mzg1ODA0MDI5OTEsInBheWxvYWQiOiJ7XCJpZFwiOjEsXCJ0b2tlblwiOm51bGwsXCJ0eXBlXCI6XCJtYW5hZ2VyX1wiLFwidXJsXCI6bnVsbH0ifQ.za9jMT8GDflhF0is_qim5FZ7spTIQbwAWCqqjeYW_AU |
Token是用.分割成三段
Header 头部(标题包含了令牌的元数据,并且包含签名和/或加密算法的类型)
Payload 加密的用户相关信息(userId)
Signature 签名/签证
三、 使用Iterceptor设置需要验证和放行接口
- 自定义Iterceptor实现WebMvcConfigurer重写addInterceptors(InterceptorRegistry)
@Configuration
|
addInterceptor设置自定义拦截规则
excludePathPatterns中设置的接口路径直接放行不验证token
2.定义拦截规则
@Component
|
3.验证token
/**
|