一,为什么要用JWT
在探讨会话跟踪方案时,传统上主要有三种常见的方式,分别是 Cookie、Session 和令牌(Token)。而在当今的 Web 开发中,JWT(JSON Web Token)作为一种令牌技术,正逐渐受到广泛的关注和应用。
Cookie 是存储在客户端浏览器中的一小段数据,服务器通过设置 Cookie 来标识用户会话。然而,Cookie 存在一些局限性,例如受到浏览器同源策略的限制,可能会被用户禁用,且在跨域请求中存在一定的复杂性。
Session 则是将用户相关的数据存储在服务器端。每个用户的会话数据都在服务器内存中保存,这在处理大量并发用户时可能会给服务器带来较大的内存压力。此外,当服务器进行分布式部署或负载均衡时,Session 共享和同步也会成为一个棘手的问题。
相比之下,JWT 具有诸多优势。首先,JWT 以紧凑的 JSON 格式进行编码,易于在不同的系统和服务之间传输。其次,它不依赖于服务器端的存储,减少了服务器的资源消耗和维护成本。再者,JWT 可以轻松地在不同的域和应用之间共享,适用于微服务架构和分布式系统。
例如,在一个多服务的架构中,如果使用 Session 来跟踪用户会话,当用户的请求在不同的服务之间跳转时,需要进行 Session 数据的同步和传递,这增加了系统的复杂性和潜在的错误风险。而使用 JWT,每个服务都可以独立地验证和解析令牌,获取用户的相关信息,无需依赖其他服务或共享存储。
又如,在跨域的场景中,Cookie 可能会因为同源策略而无法正常工作,而 JWT 则可以毫无障碍地在不同域之间传递和验证,为实现跨域的用户认证和授权提供了便捷的解决方案。 综上所述,JWT 在会话跟踪方面具有独特的优势,能够更好地满足现代 Web 应用的需求。
二,JWT的介绍
JWT,官网https://jwt.io/
由三个部分组成,为表头,载荷,和签名
表头:记录令牌的类型,签名算法等
载荷:携带一些自定义信息,默认信息等
签名:防止token被篡改,确保安全性
三,JWT在Java中的应用
由于java版本的不断更迭,jwt之前的方法即导入jjwt已经不适用,那么现在我来介绍如何在Java高级版本里使用JWT令牌技术
1.我们需要导入合适的依赖
选择合适的版本导入依赖,下面以4.4.0版本来使用
<!-- https://mvnrepository.com/artifact/com.auth0/java-jwt -->
<dependency>
<groupId>com.auth0</groupId>
<artifactId>java-jwt</artifactId>
<version>4.4.0</version>
</dependency>
二,我们在测试类里进行测试(以HS256为例
//这个是用来生成token的
try {
Algorithm algorithm = Algorithm.HMAC256("自己设置的密钥");
String token = JWT.create()
.withIssuer("JWT令牌的发行者")
.sign(algorithm);
System.out.println(token);
} catch (JWTCreationException exception){
// Invalid Signing configuration / Couldn't convert Claims.
}
String token = "上面生成token里的token";
DecodedJWT decodedJWT;
try {
Algorithm algorithm = Algorithm.HMAC256("自己设置的密钥");
// 定义了使用 HMAC256 算法,并传入密钥 "自己设置的密钥" 用于验证
JWTVerifier verifier = JWT.require(algorithm)
// specify any specific claim validations
.withIssuer("auth0")
// 要求 JWT 令牌的发行者(issuer)为 "auth0"
// reusable verifier instance
.build();
// 构建了一个 JWT 验证器
decodedJWT = verifier.verify(token);
// 使用构建好的验证器对给定的令牌(token)进行验证,并将解码后的结果存储在 decodedJWT 中
} catch (JWTVerificationException exception) {
// 如果验证过程中出现签名无效或声明(claims)不符合要求的情况,会捕获这个异常
// Invalid signature/claims
}