JSON Web令牌(JWT):授权与身份验证

时间:2018-01-22 16:43:25

标签: java json jwt

JWT术语一直困扰着我,原因很少。 JWT适用于授权还是仅适用于身份验证?

如果我错了,请纠正我,但我一直认为授权是允许某人访问资源的行为,但JWT似乎没有任何实际允许访问给定资源的用户的实现。所有JWT实现都在谈论为用户提供令牌。然后,每次调用时都会将此令牌传递给后端服务端点,在后端服务端点检查其是否有效以及是否授予了有效访问权限。因此,我们可以将JWT用于任何用户的身份验证,但我们如何限制对特定有效用户的访问?

我们如何使用JWT根据他们的角色限制少数用户? JWT是否也提供任何类型的授权细节,或者它只是向我们提供认证?

提前感谢您的帮助并耐心地阅读我的疑问。

4 个答案:

答案 0 :(得分:7)

使用特定于claims的令牌可以使用 JWT 实现

授权

Json Web Token 中打包为声明的许多其他用户信息可以在令牌中预先填写特定权限,稍后可以由授权服务拦截。

通常,授权是基于权限的,其中权限用于限制对api端点的访问(也可用于授予用户对前端应用程序上的视图的访问权限)。

这里有一个示例 JWT 标记,它具有权限元素:

{
  "UserInfo": {
    "id": "#{USER_ID}",
    "roles": {
      "#{ROLE_NAME}": "#{ROLE_ID}"
    },
    "permissions": {
      "#{PERMISSION_NAME}": "#{PERMISSION_ID}",
    }
  },
  "exp": 1488888888
}

答案 1 :(得分:4)

JWT可用于两个目的:

  1. 身份验证(如您所说)
  2. 信息交流。
  3. 第二部分是有趣的部分。 JWT包含:

    • 标题:包含算法和令牌类型
    • 有效负载:哪些是关于实体(通常是用户)和其他元数据的陈述。索赔有三种类型:注册,公开和私人索赔。
    • 签名:签名用于验证JWT的发件人是否是其所说的人,并确保邮件在此过程中未被更改。

    有效负载可以包含有关用户的信息,例如权限列表。 这样您就可以将其用于授权。

    来自jwt.io的例子:

    eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ
    

    包含:

    {
      "alg": "HS256",
      "typ": "JWT"
    }
    {
      "sub": "1234567890",
      "name": "John Doe",
      "admin": true
    }
    

    您可以看到有效负载包含有关管理权限的标识和信息。由于有效负载签名,您可以信任这些数据。

答案 2 :(得分:1)

用户首先登录。一旦用户通过登录过程,或者我们说一旦用户通过身份验证,您就可以签署 jwt 令牌并将其发送给用户。这是 node.js 片段

async postLogin(req, res, next) {
    // parse the req.body, get the email,password
    // check if the email exist, if exists check the passord
    // now you are sure credentials are true, create the jwt.
    const token = jwt.sign({ _id: this._id, email: this.email }, "this-is-secret", {
  expiresIn: "1h",
  res
    .status(200)
    .header("x-auth-token", token)
    .json({ token, userId: existingUser._id.toString() });
   });
  }

现在客户端会把它保存到localStorage。 (为简单起见,我使用 localStorage)。在客户端,用户发送 post 请求登录并获取我上面发送的内容。它将获取令牌并保存它。因为是异步请求,所以会是这样。这是一些用于演示的反应代码:

  .then(resData => {
    localStorage.setItem('token', resData.token);
    localStorage.setItem('userId', resData.userId);

关于令牌的一件事,浏览器不会自动发送它,所以客户端会手动将它附加到请求中。

fetch(url, {
      method: "post",
      headers: {
        Authorization: 'Bearer ' + localStorage.getItem('token')
      }
    })

一旦您的服务器收到请求,您就会检查传入的令牌,如果它是有效的令牌,您将授权用户访问某些路由或服务。因此用户将获得授权。

身份验证是识别用户并验证他们声称是谁的过程。验证身份的最常见和最明显的因素之一是密码。如果用户名与密码凭据匹配,则表示身份有效,系统授予用户访问权限,因此我们说用户已通过身份验证

答案 3 :(得分:0)

JWT适用于授权还是仅适用于身份验证?

这个问题的答案在于RFC7519标准的以下几行:

JSON Web令牌(JWT)是一种紧凑的声明表示格式 适用于空间受限的环境,例如HTTP 授权标头和URI查询参数。

JWT似乎没有任何实现实际上允许用户访问给定资源的实现。

我要说的是,您对此的理解需要一些改进;-) 实际上,JWT具有名为Claims的结构,您可以在其中找到与授权相关的主题。

您所理解的其余部分没有遵循正确的顺序。实际上,有一个丢失的部分叫做令牌发行者。该人员负责对JWT令牌请求者进行身份验证,并且仅当身份验证过程成功且请求者被授权时,才发出JWT令牌。然后可以通过检查签名来验证已发布的JWT令牌,这意味着,已通过令牌发行者(如Identity Server)发行的令牌将包含消息的哈希码,这将允许令牌的使用者再次检查签名。签名(哈希码),以确保在客户端-服务器之间的过渡期间未通过未经授权的访问修改令牌。然后,如果令牌是有效令牌,则消费者在下一步可以提取令牌(JWT)声明以处理授权部分。