1、引用官网对JWT的描述,翻译意思大概如下:
JWT全称为JSON Web Token,是一个开放的标准(RFC 7519),它定义了一个紧凑且自包含的方式,用于在各方之间以JSON对象安全地传输信息。这些信息可以通过数字签名进行验证和信任。可以使用密匙(使用HMAC算法)或使用RSA的公钥/私钥对来对JWT进行签名。
2、JWT官网:https://jwt.io/
如果你对公钥、私钥、数字签名等概念不熟悉,可以看下这几篇文章:
从《天才枪手》学到的对称加密知识,你确定不看看?
非对称加密,给你极致的安全感!
Hash算法给你的珍藏文件烙上独一无二的DNA
一文带你整明白到底什么是数字签名?
如果你懒得看,我在此简单说明下,他们三者本质上都是复杂的字符串!
下列场景中使用JSON Web Token是很有用的:
(1)Authorization (授权) : 这是使用JWT的最常见场景。一旦用户登录,后续每个请求都将包含JWT,允许用户访问该令牌允许的路由、服务和资源。单点登录是现在广泛使用的JWT的一个特性,因为它的开销很小,并且可以轻松地跨域使用。
(2)Information Exchange (信息交换) : 对于安全的在各方之间传输信息而言,JSON Web Tokens无疑是一种很好的方式。因为JWT可以被签名,例如,用公钥/私钥对,你可以确定发送人就是它们所说的那个人。另外,由于签名是使用头和有效负载计算的,您还可以验证内容没有被篡改。
JWT由三部分组成,这些部分由点(.)分隔,分别是:
- 头部(Header)
- 载荷(playload)
- 签名(signature)
因此,JWT通常如下所示:
xxxxx.yyyyy.zzzzz
1)头部(Header)
头部,是用来描述这个token是什么类型,采用了何种加密算法;头部一般有两部分信息:令牌的类型(即JWT)和所使用的签名算法,例如HMAC SHA256或RSA。头部一般使用base64加密,加密后如:eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9
,解密后如下:
{ "typ": "JWT", "alg": "HS256" }
2)载荷(playload)
载荷,一般存放一些有效的信息,用来传递数据。官方提供的几个标准字段,同时也可以自己往里面加自定义的字段和内容,用来存放一些不敏感的用户信息。可以简单的把它想像成一个Map集合。jwt的标准定义包含五个字段:
iss
:该JWT的签发者sub
: 该JWT所面向的用户aud
: 接收该JWT的一方exp(expires)
: 什么时候过期,这里是一个Unix时间戳iat(issued at)
: 在什么时候签发的
这个只是JWT的定义标准,不强制使用。另外自己也可以添加一些公开的不涉及安全的方面的信息。载荷的格式示例类似如下:
{ "sub": "1234567890", "name": "John Doe", "admin": true }
3)签名(signature)
签名,主要是将header
和payload
的base64
编码后内容用点拼接在一起然后进行加密生成签名。服务端需要利用这签名来校验token是否被篡改(验签),这也是JWT最后一个部分。该部分是使用了header指定的算法(如:HS256)加密后的数据,包含三个部分:
header
(base64加密后的)payload
(base64加密后的)secret
私钥
secret是保存在服务器端的,jwt的签发生成也是在服务器端的,secret就是用来进行jwt的签发和jwt的验证,所以,它就是你服务端的私钥,在任何场景都不应该泄露出去。一旦客户端得知这个secret, 那就意味着客户端是可以自我签发jwt了。
为了得到签名部分,你必须有编码过的header、编码过的payload、一个秘钥,签名算法是header中指定的那个,然对它们签名即可。例如:
HMACSHA256(base64UrlEncode(header) + "." +base64UrlEncode(payload),secret)
签名是用于验证消息在传递过程中有没有被更改,并且,对于使用私钥签名的token,它还可以验证JWT的发送方是否为它所称的发送方。
在认证的时候,当用户用他们的凭证成功登录以后,一个JSON Web Token将会被返回。此后,token就是用户凭证了,你必须非常小心以防止出现安全问题。一般而言,你保存令牌的时候不应该超过你所需要它的时间。
无论何时用户想要访问受保护的路由或者资源的时候,用户代理(通常是浏览器)都应该带上JWT,典型的,通常放在Authorization header
中,用Bearer schema
,header应该看起来是这样的:
Authorization: Bearer <token>
服务器上的受保护的路由将会检查Authorization header
中的JWT是否有效,如果有效,则用户可以访问受保护的资源。如果JWT包含足够多的必需的数据,那么就可以减少对某些操作的数据库查询的需要,尽管可能并不总是如此。如果token是在授权头(Authorization header)中发送的,那么跨源资源共享(CORS)将不会成为问题,因为它不使用cookie。
JWT与OAuth的区别 -OAuth2是一种授权框架 ,JWT是一种认证协议 -无论使用哪种方式切记用HTTPS来保证数据的安全性 -OAuth2用在使用第三方账号登录的情况(比如使用weibo, qq, github登录某个app),而JWT是用在前后端分离, 需要简单的对后台API进行保护时使用。