JWT 实战

上一篇我们讲解了 JWT 的基本原理和结构 你了解JWT吗?,接下来我们具体实战一下!

1. 引入依赖

1
2
3
4
5
6
<!--引入jwt-->
<dependency>
  <groupId>com.auth0</groupId>
  <artifactId>java-jwt</artifactId>
  <version>3.4.0</version>
</dependency>

2. 编写工具类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
@Slf4j
public class JwtUtils {
 
    private static final String SIGN = "!Q@WXDjksWE$";
 
    /**
     * 生成 Token  header.payload.signature
     */
    public static String getToken(Map<String, String> map) {
        // 指定令牌的过期时间为 7 天
        Calendar instance = Calendar.getInstance();
        instance.add(Calendar.DATE, 7);
 
        // 创建 Jwt builder
        JWTCreator.Builder builder = JWT.create();
 
        // 循环添加 payload
        map.forEach((k, v) -> builder.withClaim(k, v));
 
        // 指定过期时间 签名 指定加密算法和密钥
        String token = builder.withExpiresAt(instance.getTime()).sign(Algorithm.HMAC256(SIGN));
        log.info("token = {}", token);
        return token;
    }
 
    /**
     * 1)验证 Token 合法性【签名一样,token合法,过期校验】
     * 2)如果 Token 校验过程中出现错误,直接抛异常
     *  - SignatureVerificationException:    签名不一致异常
     *  - TokenExpiredException:             令牌过期异常
     *  - AlgorithmMismatchException:        算法不匹配异常
     *  - InvalidClaimException:         失效的payload异常
     */
    public static void verify(String token) {
        JWT.require(Algorithm.HMAC256(SIGN)).build().verify(token);
    }
 
    /**
     * 获取 token 中信息【先校验 token 合法性,然后再拿 token 中信息】
     */
    public static DecodedJWT getTokenInfo(String token) {
        DecodedJWT verify = JWT.require(Algorithm.HMAC256(SIGN)).build().verify(token);
        return verify;
    }
 
}

3. 测试用例

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
@SpringBootTest
@Slf4j
public class TestJwt {
 
    @Test
    public void testJwt() {
        /**
         * JWT 中 header 默认就是 {"alg": "HS256", "typ": "JWT"} 一般不做改变
         */
        HashMap<String, Object> map = new HashMap<>();
        // 指定令牌的过期时间为 20s
        Calendar instance = Calendar.getInstance();
        instance.add(Calendar.SECOND, 1000);
 
        // 获取令牌
        String token = JWT.create()
                .withHeader(map)
                .withClaim("userId", 21)        // payload
                .withClaim("username", "zhangsan"// payload
                .withExpiresAt(instance.getTime())           // 指定令牌的过期时间
                .sign(Algorithm.HMAC256("!Q@WXDjksWE$"));    // 签名,指定加密算法和密钥
 
        log.info("token = {}", token);
    }
 
    @Test
    public void testValid() {
        // 创建验证对象
        JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256("!Q@WXDjksWE$")).build();
 
        // 校验,获取校验后的结果对象信息【需要将上一个 test 执行的 token 字符串传入,进行校验】
        DecodedJWT verify = jwtVerifier.verify("eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE2MDMzMzU3NzUsInVzZXJJZCI6MjEsInVzZXJuYW1lIjoiemhhbmdzYW4ifQ.<br>bLzXG8-QpcwmQSEBEtkoZVBySG2XO5I462fFwTN8MLQ");
 
        log.info("header = {}", verify.getHeader());
        log.info("userId = {}, usernmae = {}", verify.getClaims().get("userId").asInt(), verify.getClaims().get("username").asString());
        log.info("过期时间 = {}", verify.getExpiresAt());
    }
 
}

4. 执行结果

 

 5. 总结

  1)JWT (Json Web Token) 令牌格式:【token = head.payload.signature】

  2)校验Token顺序:a. 校验签名算法是否一样; b. 校验签名是否一样【即:head patload secret 是否一样】;c. 校验Token是否有效【前后是否一致 equals】;d. 校验Token是否过期。

posted @   菜鸟的奋斗之路  阅读(710)  评论(0编辑  收藏  举报
编辑推荐:
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
阅读排行:
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 地球OL攻略 —— 某应届生求职总结
· 提示词工程——AI应用必不可少的技术
· Open-Sora 2.0 重磅开源!
· 周边上新:园子的第一款马克杯温暖上架
点击右上角即可分享
微信分享提示