JWT:解决前后端分离和微服务的用户会话跟踪问题
JWT
Json web token (JWT), 是为了在网络应用环境间传递声明而执行的一
种基于 JSON 的开放标准(
(RFC 7519).定义了一种简洁的,自包含的方法用于
通信双方之间以 JSON **对象的形式安全的传递信息。**因为数字签名的存在,这些 信息是可信的,
JWT 可以使用 HMAC 算法或者是 RSA 的公私秘钥对进行签名。起源
说起 JWT,我们应该来谈一谈基于 token 的认证和传统的 session 认证的 区别。
与传统sessio验证的区别:
传统的 session 认证
我们知道,http 协议本身是一种无状态的协议,而这就意味着如果用户向 我们的应用提供了用户名和密码来进行用户认证,那么下一次请求时,用户还要 再一次进行用户认证才行,因为根据 http 协议,我们并不能知道是哪个用户发 出的请求,所以为了让我们的应用能识别是哪个用户发出的请求,我们只能在服 务器存储一份用户登录的信息,这份登录信息会在响应时传递给浏览器,告诉其 保存为 cookie,以便下次请求时发送给我们的应用,这样我们的应用就能识别请 求来自哪个用户了,这就是传统的基于 session 认证。 但是这种基于 session 的认证使应用本身很难得到扩展,随着不同客户端用 户的增加,独立的服务器已无法承载更多的用户,而这时候基于 session 认证应 用的问题就会暴露出来
基于 session 认证所显露的问题:
Session: 每个用户经过我们的应用认证之后,我们的应用都要在服务端做 一次记录,以方便用户下次请求的鉴别,通常而言 session 都是保存在内存中, 而随着认证用户的增多,服务端的开销会明显增大。
扩展性: 用户认证之后,服务端做认证记录,如果认证的记录被保存在内存 中的话,这意味着用户下次请求还必须要请求在这台服务器上,这样才能拿到授 权的资源,这样在分布式的应用上,相应的限制了负载均衡器的能力。这也意味 着限制了应用的扩展能力。
**CSRF (跨站请求伪造)😗*因为是基于 cookie 来进行用户识别的, cookie 如果 被截获,用户就会很容易受到跨站请求伪造的攻击。
基于 token 的鉴权机制
基于 token 的鉴权机制类似于 http 协议也是无状态的,它不需要在服务端 去保留用户的认证信息或者会话信息。这就意味着基于 token 认证机制的应用 不需要去考虑用户在哪一台服务器登录了,这就为应用的扩展提供了便利。
- 用户使用账号和密码发出 post 请求;
- 服务器使用私钥创建一个 jwt;
- 服务器返回这个 jwt 给浏览器;
- 浏览器将该 jwt 串在请求头中像服务器发送请求;
- 服务器验证该 jwt;
- 返回响应的资源给浏览器。
JWT的主要引用场景及优点
身份认证在这种场景下,一旦用户完成了登陆,在接下来的每个请求中包含
JWT,**可以用来验证用户身份以及对路由,服务和资源的访问权限进行验证。**由
于它的开销非常小,可以轻松的在不同域名的系统中传递,所有目前在单点登录 【前后端分离 微服务】**(SSO)**中比较广泛的使用了该技术。 信息交换在通信的双方之间使用 JWT 对 数据进行编码是一种非常安全的方式,由于它的信息是经过签名的,可以确保发 送者发送的信息是没有经过伪造的。
优点:
1**.简洁(Compact)**: 可以通过 URL,POST 参数或者在 HTTP header 发送,因为数 据量小,传输速度也很快
2.自包含(Self-contained):负载中包含了所有用户所需要的信息,避免了多次 查询数据库
3.因为 Token 是以 JSON 加密的形式保存在客户端的,所以 JWT 是跨语言的,原 则上任何 web 形式都支持。
4.不需要在服务端保存会话信息,特别适用于分布式微服务。
JWT的构成:
JWT 是由三段信息构成的,将这三段信息文本用.链接一起就构成了 Jwt 字符 串。就像这样:
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab3 0RMHrHDcEfxjoYZgeFONFh7HgQ 32位
第一部分我们称它为头部(header),第二部分我们称其为载荷(payload, 用户 的信息),第三部分是签证(signature).
第一部分
header
jwt 的头部承载两部分信息: 声明类型,这里是 jwt 声明加密的算法 通常直接使用 HMAC HS256 完整的头部就像下面这样的 JSON:
{
‘typ’: ‘JWT’,
‘alg’: ‘HS256’
}
然后将头部进行 base64 转码,构成了第一部分.
eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9
10010101 01010101
100101 010101 010100
第