JWT简介

JWT-Wikipedia

        JWT( $JSON\ \ Web\ \ Token$ )是一种基于JSON的用于创建可选签名或可选加密的数据的互联网标准。Token使用一个私钥或者公钥进行签名,持有私钥或者公钥的一方可以验证令牌的合法性。Token被设计为紧凑且安全的,尤其适用于Web浏览器单点登录 ( Single-sign-on, $SSO$ ) 场景。JWT声明一般用于在身份提供者和服务提供者之间传递用户身份信息,或者用于业务流程要求的任何其他类型的声明。

        在传统的session认证中,通常使用cookie来保存用户的身份信息,方便下一次请求。由于session是存储在内存中的,因此存在开销隐患。而且使用cookie也意味着存在着CSRF问题。使用JWT进行认证时,用户在成功认证登录过后,将会得到一个tokenToken会保存在本地(也可以保存在session或者cookie中),而不是传统的在服务器上创建一个session并返回cookie。每当用户想要访问受保护的资源时,用户代理需要发送JWTJWT通常包含在请求头中。通过使用JWT,用户的状态永远也不会保存在服务器中。当接收到请求时,服务器将会检查JWT的有效性。由于JWT是独立的,存储着所有必要的信息,因此可以减少数据库查询的次数。

JWT的结构

        JWT由三部分组成:$Header$, $Payload$, $Signature$ 。

1. Header

{
    "alg": "HS256",
    "typ": "JWT"
}

        $Header$ 标识用于生成签名的算法。典型的加密算法如HMAC-SHA-256, RSA-SHA-256。上例使用的是HMAC-SHA-256

2. Payload

{
    "loggedInAs": "admin",
    "iat": 1422779638
}

        $Payload$ 包含了一组声明。JWT标准注册了七个声明:

        $Payload$ 中还可以添加自定义声明,如上例的 $loggedInAs$。

3. Signature

var signature = HMAC-SHA256(
    base64urlEncoding(header) + '.' + base64urlEncoding(payload),
    'secret'
);

        $Signature$ 用于安全地验证token。使用 $Base64urlEncoding$ 对 $header$ 和 $payload$ 进行编码,再使用句点隔开,可以计算出签名。$secret$保存在服务器中,在使用指定算法生成签名的时候使用,生成哈希,确保数据不被篡改。然后再通过指定的算法,在此例中为 HMAC-SHA256, 进行加密。$Base64url$ 编码类似于 base64

        最终得到的JWT如下

const token = base64urlEncoding(header) + '.' + base64urlEncoding(payload) + '.' + base64urlEncoding(signature);

        最后在请求头中加入

Authorization: `Bearer' + token

JWT简介