JWT概念学习

JWT 全称 JSON Web Tokens ,是一个非常轻巧的规范。这个规范允许我们使用 JWT 在用户和服务器之间传递安全可靠的信息。它的两大使用场景是:认证和数据交换。

1.什么是JSON Web令牌?

  • JSON Web令牌(JWT)是一个开放标准(RFC 7519),它定义了一种紧凑且自包含的方式,用于在各方之间作为JSON对象安全地传输信息。由于此信息是经过数字签名的,因此可以被验证和信任。可以使用秘密(使用HMAC算法)或使用RSAECDSA的公钥/私钥对对JWT进行签名
  • 尽管可以对JWT进行加密以在双方之间提供保密性,但我们将重点关注已签名的令牌。签名的令牌可以验证其中包含的声明的完整性,而加密的令牌则将这些声明隐藏在其他方的面前。当使用公钥/私钥对对令牌进行签名时,签名还证明只有持有私钥的一方才是对其进行签名的一方。

在这里插入图片描述

  • 基于传统的token认证

    用户登录,服务端给返回token,并将token保存在服务端。

    以后用户再来访问时,需要携带token,服务端获取token后,再去数据库获取token进行校验

  • JWT

    用户登录,服务端给用户返回一个token(服务端不保存)

    以后用户再来访问,需要携带token,服务端获取token后,

    再做token的校验。

    优势:相比较传统的token相比,它无需在服务端保存token。

2.什么时候应该使用JSON Web令牌?

以下是JSON Web令牌有用的一些情况:

  • 授权:这是使用JWT的最常见方案。一旦用户登录,每个后续请求将包括JWT,从而允许用户访问该令牌允许的路由,服务和资源。单一登录是当今广泛使用JWT的一项功能,因为它的开销很小并且可以在不同的域中轻松使用。json web token ,一般用于用户认证(前后端分离/微信小程序/app开发)
  • 信息交换:JSON Web令牌是在各方之间安全地传输信息的好方法。因为可以对JWT进行签名(例如,使用公钥/私钥对),所以您可以确定发件人是他们所说的人。另外,由于签名是使用标头和有效负载计算的,因此您还可以验证内容是否未被篡改。

3.jwt实现过程

  • 用户提交用户名和密码给服务端,如果登录成功,使用jwt创建一个token,并给用户返回。
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

注意:jwt生成的token是由三段字符串组成,并且拼接起来。

  • 第一段字符串,HEADER头,内部包含算法/token类型。

    json转化为字符串,然后做basee64url加密(base64加密;替换±)

{
  "alg": "HS256",
  "typ": "JWT"
}
  • 第二段字符串,payload有效载荷,自定义值(你想给用户返回的信息)

    json转化为字符串,然后base64url加密(base64加密;+_)

请注意,对于已签名的令牌,此信息尽管可以防止篡改,但任何人都可以读取。除非将其加密,否则请勿将机密信息放入JWT的有效负载或报头元素中。

{
  "id": "1234",
  "name": "John Doe",
  "exp": 1516239022 #超时时间
}
  • 第三部分字符串:签名
第一步:第1,2部分密文拼接起来
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ
第二步:对前2部分密文进行HS256加密 + 加盐
第三步:对HS256加密后的密文再做base64url加密
  • 以后用户再来访问时候,需要携带token,后端需要对token进行校验

    • 获取token
    • 第一步:对token进行切割
    eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c
    
    • 第二步:对第二段进行base64Url进行解密,并获取payload信息,检测token是否已经超时?
    {
      "id": "1234",
      "name": "John Doe",
      "exp": 1516239022 #超时时间
    }
    
    • 第三步:把1,2端拼接,再次执行HS256加密(哈希不能反解)
第一步:第1,2部分密文拼接起来
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ
第二步:对前2部分密文进行HS256加密 + 加盐

密文 = base64解密(SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c)
如果相等,表示token未被修改过(认证通过)

在这里插入图片描述

4.优缺点

  1. JWT的优点:
  • 无需再服务端存储用户数据,减轻服务端压力
  • 轻量级,json风格,比较简单
  • 跨语言
  1. JWT的缺点:
  • token一旦签发,无法修改
    • 无法更新token有效期,用户登录状态刷新难以实现
    • 无法销毁一个token,服务端不能对用户状态进行绝对控制
  • 不包含权限控制

5.面试相关

1 .你们使用JWT做登录凭证,如何解决token注销问题(比如app登录之后)

答:jwt的缺陷是token生成后无法修改,因此无法让token失效。只能采用其它方案来弥补,基本思路如下:
方案一:
1)适当减短token有效期,让token尽快失效
2)删除客户端cookie
3)服务端对失效token进行标记,形成黑名单,虽然有违无状态特性,但是因为token有效期短,因此标记 时间也比较短。服务器压力会比较小
方案二:
1)用户登录后,生成JWT
2)把JWT的id存入redis,只有redis中有id的JWT,才是有效的JWT
3)退出登录时,把ID从Redis删除即可

2.既然token有效期短,怎么解决token失效后的续签问题?(app登录之后续签怎么解决,app如何保持一次登陆后持续保持)

答:在验证用户登录状态的代码中,添加一段逻辑:判断cookie即将到期时,重新生成一个token。比如token有效期为30分钟,当用户请求我们时,我们可以判断如果用户的token有效期还剩下10分钟,那么就重新生成token。因此用户只要在操作我们的网站,就会续签token

3.如何解决异地登录问题?

答:JWT设计为了实现无状态的登录,因此token无法修改,难以实现异地登录的判断,或者强制让登录token失效。
因此如果有类似需求, 就不应选择JWT作为登录方案,而是使用传统session登录方案。
但是,如果一定要用JWT实现类似要过,就需要在Redis中记录登录用户的JWT的token信息,这样就成了有状态的登录,还不如一开始就选择Session方案。

6.JWT 在线工具

7.参考扩展

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值