美文网首页Swartz动物园
JSON Web Token 介绍

JSON Web Token 介绍

作者: 绝望的祖父 | 来源:发表于2017-02-04 19:17 被阅读146次
    什么是 JSON Web Token

    JSON Web Token (JWT) 是为了在网络间安全地传输信息而设计的一种协议 (RFC 7519),它以JSON对象的形式存在,并且自包含。这些信息可被验证,并添加了数字签名以防止篡改。JWT可以基于HMAC哈希算法进行签名,或者使用基于公/私钥对的RSA算法进行签名。

    首先,让我们更进一步得解释一下定义中的一些概念:

    • 协议:JWT令牌的尺寸非常小,因此能够通过URL,POST请求体,或者直接附加到HTTP请求头中。另外,尺寸小意味着传输速度会非常快
    • 自包含:JWT的载荷包含了所有需要的用户信息,避免了对数据库的多次查询
    什么时候需要使用 JSON Web Token

    以下是一些JSON Web Token的常用场景:

    • 认证:这是JWT最常用的场景。一旦用户登录以后,之后的每一个请求将会包含JWT令牌,并允许用户访问被保护的路由,服务和资源。由于其较小的开销并能够方便得跨域使用,单点登录系统目前已广泛使用JWT。
    • 信息交换:由于JSON Web Token能够被签名,因此是一种安全地交换信息的好方法。例如,使用公私钥对进行签名,你能够确保消息的发送方不是恶意伪造的,另外,由于签名是通过载荷和头部计算出来的,因此你能够确保消息内容没有被篡改过。
    JSON Web Token的数据结构

    JSON Web Token由三部分组成,并通过英文句号(.)隔开:

    • 头部
    • 载荷
    • 签名

    因此,一个典型的JWT令牌看起来会像这样:
    xxxxx.yyyyy.zzzzz

    头部

    典型的头部信息包含两部分:令牌的类型 (JWT),以及签名所使用的哈希算法,例如 HMAC, SHA256, RSA

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

    然后,这段JSON对象将使用Base64编码成字符串并放入JWT令牌的第一部分

    载荷

    令牌的第二部分被称为载荷,载荷中包含了声明。声明是一些实体描述(例如用户)以及相关的元数据。有三种类型的声明:reserved, public和private

    • Reserved 声明:这一类预定义的声明并不是强制性的,但是推荐使用。包括:iss(发布者),exp(过期时间),sub(主题),aud(受众)等等
    • Public 声明:公共声明可以添加任何信息。不过为了避免冲突,用户定义时应遵守IANA JSON Web Token Registry规范,或者包含一个防止名称冲突的命名空间,比如URI
    • Private 声明:这部分声明由信息交换的双方自行定义

    一个载荷的例子如下:

    {
        "sub": "1234567890",
        "name": "John Doe",
        "admin": true
    }
    

    然后使用Base64对其进行编码,得到JWT的第二部分。

    签名

    为了创建签名,你需要拿到编码后的头部,编码后的载荷,以及一个密钥,签名的算法在头部中进行指定。
    例如,你想要使用 HMAC SHA256 算法进行签名,那么签名函数看起来将会是如下的格式:

    HMACSHA256(
        base64UrlEncode(header) + "." + 
        base64UrlEncode(payload),
        secret
    )
    

    签名用来验证令牌的发送者不是伪造的,并确保信息不被篡改

    把所有部分放在一起

    最终的令牌由三部分 Base64 字符串拼接而成,中间使用英文句点(.)隔开,因此令牌可以轻松得在 HTML 和 HTTP 环境中进行传递

    以下展示了之前的各个部分组合之后的完整JWT令牌

    encoded-jwt3.png
    你可以使用jwt.io Debugger进行解码以及验证
    JSON Web Token 如何工作

    在认证场景中,相较于传统的模式(在服务端生成会话并返回一个cookie),当用户使用他们的凭据成功登录以后,一个JSON Web Token将会被返回,该令牌必须被保存在本地(典型的场景是保存在本地存储中,不过cookie也常常用来保存这一类信息)。

    无论何时,当用户想要访问一个受保护的资源,他必须将JWT发送到服务端,典型的发送方式是通过 Authorization 请求头字段,并指定 Bearer 模式。请求头的内容看起来会像下面这样:

    Authorization: Bearer <token>
    

    这是一个无状态的认证机制,用户信息永远也不会保存在服务器的内存中。服务器受保护的路由会检查通过Authorization头传递的令牌是否是一个正确的令牌,如果检查通过,用户将被允许访问受保护的资源。由于JWT是自包含的,所有必要的信息都包含在令牌中,进而减少了查询数据库所需要的时间。

    正因为如此,JWT允许你的服务完全依赖于无状态的数据接口。它不关心你的APIs寄宿在哪个域名之下,因此跨域访问(CORS)将不会成为一个问题(使用cookie就不行)

    下面的图表展示了整个处理流程


    jwt-diagram.png

    相关文章

      网友评论

        本文标题:JSON Web Token 介绍

        本文链接:https://www.haomeiwen.com/subject/odqsittx.html