SpringBoot整合JWT框架及JWT介绍
⼀、传统Session认证
1、认证过程:
1、⽤户向服务器发送⽤户名和密码。
2、服务器验证后在当前对话(session)保存相关数据。
springboot框架的作用3、服务器向返回sessionId,写⼊客户端 Cookie。
4、客户端每次请求,需要通过 Cookie,将 sessionId 回传服务器。
5、服务器收到 sessionId,验证客户端。
2、问题缺陷
1、session保存在服务端,客户端访问⾼并发时,服务端压⼒⼤。
2、扩展性差,服务器集,就需要 session 数据共享。
⼆、JWT简介
  JWT(全称:JSON Web Token),在基于HTTP通信过程中,进⾏⾝份认证,JWT它是⽬前最流⾏的跨域⾝份验证解决⽅案。
1、认证流程
  JWT的⼯作原理:是在服务器⾝份验证之后,将⽣成⼀个JSON对象,这个 JSON 对象⾥存了⼀些⽤户的信息,⽐如id、role、name等(如:{"name": "**","role": "Admin","id":"**","Expire": "***"}),但是这个JSON对象肯定不能直接返回,所以需要加密⼀下,⽣成⼀个token,就是⼀个加密字符串,然后将这个 token 发送回⽤户之后,当⽤户与服务器通信时,客户端在请求中需要将这个 token ⼀起发送回服务器,服务器再解析这个 token ⽣成之前的JSON对象,然后去认证了这个⽤户。
  当然为了防⽌⽤户篡改数据,服务器将在⽣成对象时添加签名,并对发回的数据进⾏验证。
  具体流程如下:
1、客户端通过⽤户名和密码登录服务器;
2、服务端对客户端⾝份进⾏验证;
3、服务器认证以后,⽣成⼀个 JSON 对象⽣成的 token,发回客户端;
4、客户端与服务端通信的时候,都要发回这个 token;
5、服务端解析该token,然后得到这个JSON对象,获取⽤户⾝份;
6、服务端可以不必存储该Token对象,⾝份信息都可以解析出来。
2、为什么要使⽤ JWT
(1)JWT基于json,⾮常⽅便解析。
(2)可以在令牌中⾃定义丰富的内容,易扩展。
(3)通过⾮对称加密算法及数字签名技术,JWT防⽌篡改,安全性⾼。
(4)资源服务使⽤JWT可不依赖认证服务即可完成授权。
3、JWT结构
  token长这样
"token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzUxMiJ9.
eyJzdWIiOiJhZG1pbiIsImlhdCI6iZEIj3fQ.
uEJSJagJf1j7A55Wwr1bGsB5YQoAyz5rbFtF"
  上⾯的Token被⼿动格式化了,实际上是⽤"."分隔的⼀个完整的长字符串,其结构如下:
1、头部(header) 声明类型以及加密算法;
2、负载(payload) 携带⼀些⽤户⾝份信息;
3、签名(signature) 签名信息。
(1)Header:
  这个json中的typ属性,⽤来标识整个token字符串是⼀个JWT字符串;它的alg属性,⽤来说明这个JWT签发的时候所使⽤的签名和摘要算法。typ跟alg属性的全称其实是type跟algorithm,分别是类型跟算法的意思。
  之所以都⽤三个字母来表⽰,也是基于JWT最终字串⼤⼩的考虑,同时也是跟JWT这个名称保持⼀致,
这样就都是三个字符了。
  typ跟alg是JWT中标准中规定的属性名称。
(2)Payload:
  payload⽤来承载要传递的数据,它的json结构实际上是对JWT要传递的数据的⼀组声明,这些声明被JWT标准称为claims,它的⼀个“属性值对”其实就是⼀个claim(要求),每⼀个claim的都代表特定的含义和作⽤。
(3)signature
  签名是把header和payload对应的json结构进⾏base64url编码之后得到的两个串⽤英⽂句点号拼接起来,然后根据header⾥⾯alg指定的签名算法⽣成出来的。算法不同,签名结果不同。以alg: HS256为例来说明前⾯的签名是以HS256算法得到。
4、JWT使⽤⽅式
  通常推荐的做法是客户端在 HTTP 请求的头信息Authorization字段⾥⾯:
Authorization: Bearer <token>
  服务端获取JWT⽅式
String token = Header("token");
三、与SpringBoot整合
1、核⼼依赖⽂件
<!-- jjwt -->
<dependency>
  <groupId>io.jsonwebtoken</groupId>
  <artifactId>jjwt</artifactId>
  <version>0.9.1</version>
</dependency>
2、配置⽂件
/
/ 跟spring同级
config:
jwt:
# 加密密钥
secret: TestTokenSecret  // 这个⾃⼰定义
# token有效时长
expire: 3600
# header 名称
header: token
3、JWT配置代码块
@ConfigurationProperties(prefix = "config.jwt")
@Component
public class JwtConfig {
/*
* 根据⾝份ID标识,⽣成Token
*/
public String getToken (String identityId){
Date nowDate = new Date();
//过期时间
Date expireDate = new Time() + expire * 1000);
return Jwts.builder()
.setHeaderParam("typ", "JWT")
.
setSubject(identityId)
.setIssuedAt(nowDate)
.setExpiration(expireDate)
.signWith(SignatureAlgorithm.HS512, secret)
pact();
}
/*
* 获取 Token 中注册信息
*/
public Claims getTokenClaim (String token) {
try {
return Jwts.parser().setSigningKey(secret).parseClaimsJws(token).getBody();
}catch (Exception e){
e.printStackTrace();
return null;
}
}
/*
* Token 是否过期验证
*/
public boolean isTokenExpired (Date expirationTime) {
return expirationTime.before(new Date());
}
private String secret;
private long expire;
private String header;
// 省略 GET 和 SET
}
  主要是看上⾯加粗的⼀个⽣成token,⼀个解析token的⽅法咯。
  ⽹上其实也有蛮多 JwtUtil ⼯具类,可以⾃⼰搜的参考。
四、拦截⽰例
  其实⼀般都会搭配SpringSecurity使⽤,这⾥⾃定义⼀个⽰例看下1、配置Token
@Component
public class TokenInterceptor extends HandlerInterceptorAdapter {
@Resource
private JwtConfig jwtConfig ;
@Override
public boolean preHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler) throws Exception {
// 地址过滤
String uri = RequestURI() ;
if (ains("/login")){
return true ;
}
// Token 验证
String token = Header());
if(StringUtils.isEmpty(token)){
token = Header());
}
if(StringUtils.isEmpty(token)){
throw new Header()+ "不能为空");
}
Claims claims = TokenClaim(token);
if(claims == null || jwtConfig.Expiration())){
throw new Header() + "失效,请重新登录");        }
//设置 identityId ⽤户⾝份ID
request.setAttribute("identityId", Subject());
return true;
}
}
2、注册
@Configuration
public class WebConfig implements WebMvcConfigurer {
@Resource
private TokenInterceptor tokenInterceptor ;
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(tokenInterceptor).addPathPatterns("/**");
}
}
  然后就可以写接⼝测试了。

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。