关于安全:JWT-跨域认证详解及应用场景

48次阅读

共计 2627 个字符,预计需要花费 7 分钟才能阅读完成。

JSON Web Token(缩写 JWT)是目前最风行的 跨域认证 解决方案。

JWT 比照 session

JWT 认证与基于 session 的认证最大的区别是:

  1. JWT 的所有数据都保留在客户端,每次发送申请时都发回服务器;而 session 只须要在客户端保留一个 session_id,其余数据都保留在服务器端,每次发送申请时只需发送 session_id 到服务器,服务器依据发送的 session_id 取出保留在服务器端的其余数据。
  2. JWT 的数据能够放在 Cookie 外面主动发送,也能够放在 HTTP 申请的头部发送,形式较为灵便;而原生 session 须要基于 Cookie 发送,存在跨域问题。

JWT 的利用场景

JWT 次要用于须要 跨域 进行认证的场景,例如服务 A 在认证了用户身份后,颁发一个很短过期工夫的 JWT 给客户端,客户端在向服务 B 的申请中带上该 JWT,则服务 B 能够通过验证该 JWT 来判断用户是否有权执行服务 B 上的相干操作。

以下场景不倡议应用 JWT 作为认证:

  1. 同域名的前后端拆散的我的项目。基于 session 进行认证即可。
  2. 不同域名的前后端拆散的我的项目、挪动端我的项目。因为不同域名无奈基于 Cookies 进行认证,但能够应用在 HTTP HEADER 中寄存 token 的形式进行认证。
  3. 服务器端应用集群的我的项目。能够通过部署认证令牌长久层,多个应用服务器共用长久层进行认证。

JWT 的原理

JWT 的原理是,服务器认证胜利后,生成一个 JSON 对象,发回给客户端:

{
  "姓名": "张三",
  "角色": "管理员",
  "到期工夫": "2018 年 7 月 1 日 0 点 0 分"
}

之后客户端与服务端通信时,都要发回这个 JSON 对象。服务器齐全只靠这个对象认证客户端身份。为了避免客户端篡改数据,服务器在生成这个对象的时候,会加上签名。

这样服务器就不须要保留任何 session 数据了,也就是说,服务器变成无状态了,从而比拟容易实现扩大。

JWT 的数据结构

JWT 次要由三个局部组成:

  • Header(头部)
  • Payload(负载)
  • Signature(签名)

三个局部之间应用 . 连贯:

Header.Payload.Signature

Header 局部

Header 局部是一个 JSON 对象,形容 JWT 的元数据,例如:

{
  "alg": "HS256",
  "typ": "JWT"
}
  • alg属性示意签名的算法(algorithm),默认是 HMAC SHA256(写成 HS256)
  • typ属性示意这个令牌的类型(type),JWT 令牌对立写为JWT

而后将下面的 JSON 对象应用 Base64URL 算法转成字符串。

Payload

Payload 局部也是一个 JSON 对象,用来寄存理论须要传递的数据。JWT 官网规定了 7 个字段,供选用:

  • iss (issuer):签发人
  • exp (expiration time):过期工夫
  • sub (subject):主题
  • aud (audience):受众
  • nbf (Not Before):失效工夫
  • iat (Issued At):签发工夫
  • jti (JWT ID):编号

除了官网字段,你还能够在这个局部定义公有字段,例如:

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

留神,JWT 默认是不加密的,任何人都能够读到,所以不要把机密信息放在这个局部。

这个 JSON 对象也要应用 Base64URL 算法转成字符串。

Signature

Signature 局部是对前两局部的签名,避免数据篡改。

首先,须要指定一个密钥(secret)。这个密钥只有服务器才晓得,不能泄露给客户端。而后,应用 Header 外面指定的签名算法(默认是 HMAC SHA256),依照上面的公式产生签名。

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

算出签名当前,把 Header、Payload、Signature 三个局部拼成一个字符串,每个局部之间用 ” 点 ”(.)连贯,就能够返回给用户。

Base64URL

后面提到,Header 和 Payload 串型化的算法是 Base64URL。这个算法跟 Base64 算法根本相似,但有一些小的不同。

JWT 作为一个令牌(token),有些场合可能会放到 URL 中(比方 api.example.com/?token=xxx)。Base64 有三个字符 +/=,在 URL 外面有非凡含意,所以要被替换掉:=被省略、+替换成 -/ 替换成_。这就是 Base64URL 算法。

JWT 的应用

客户端收到服务器返回的 JWT,能够贮存在 Cookie 外面,也能够贮存在 localStorage。

尔后,客户端每次与服务器通信,都要带上这个 JWT。你能够把它放在 Cookie 外面主动发送,然而这样不能跨域,所以更好的做法是放在 HTTP 申请的头信息 Authorization 字段外面。

Authorization: Bearer <token>

JWT 的几个特点

(1)JWT 默认是不加密,但也是能够加密的。生成原始 Token 当前,能够用密钥再加密一次。

(2)JWT 不加密的状况下,不能将机密数据写入 JWT。

(3)JWT 不仅能够用于认证,也能够用于替换信息。无效应用 JWT,能够升高服务器查询数据库的次数。

(4)JWT 的最大毛病是,因为服务器不保留 session 状态,因而 无奈在应用过程中废止某个 token,或者更改 token 的权限。也就是说,一旦 JWT 签发了,在到期之前就会始终无效,除非服务器部署额定的逻辑。

(5)JWT 自身蕴含了认证信息,一旦泄露,任何人都能够取得该令牌的所有权限。为了缩小盗用,JWT 的有效期应该设置得比拟短。对于一些比拟重要的权限,应用时应该再次对用户进行认证。

(6)为了缩小盗用,JWT 不应该应用 HTTP 协定明码传输,要应用 HTTPS 协定传输。

JWT 应用的一些疑难

  1. JWT 无奈解决多个设施排他登录问题,例如用户在 A 设施曾经登录,而后在 B 设施再次登录,无奈让 A 的登录过期。可通过在服务端保护一张签发 token 的清单,生成新的 JWT 时将旧的 JWT 标记为生效。但这样做和 session 比就没有什么劣势了,反而还引入了安全性问题。
  2. JWT 无奈解决单点登录问题,例如用户在 a.com 域名曾经登录,而后拜访同一公司的 b.com 域名,无奈在 b.com 域名实现主动同步登录。可通过其余单点登录计划解决。

参考:http://www.ruanyifeng.com/blo…

正文完
 0