JSON Web Tokens 的正确使用
Posted
技术标签:
【中文标题】JSON Web Tokens 的正确使用【英文标题】:Correct usage of JSON Web Tokens 【发布时间】:2018-08-25 18:30:42 【问题描述】:在澄清了一些想法之后,问题更侧重于JWT的正确使用。
我们只讨论编码(未加密)的 JWT,我们只考虑使用对称密钥的 HMAC
,我们称之为 p@$$w0rd
,它将用于签署 JWT。
我们知道 JWT 不应该包含敏感信息,因为它们不会隐藏任何数据,因为有效负载只是 Base64 编码,它们只应该通过 signature
验证信息来自正确的客户端.
在我们的例子中,我们发送 role
的目的是在我们的 Web 应用程序中显示/隐藏某些元素。
在具有admin
角色的用户中,将看到创建/修改/删除用户等的链接作为示例。
场景
A
-> 一个admin
用户,在登录时从服务器(颁发者)请求 JWT
Server
-> 发出带有 userID
、userName
、role
声明的 JWT,并带有过期日期。
A
-> 应该在对server
的所有进一步 API 请求时发送此 JWT 令牌,服务器将使用此令牌进行身份验证。
B
-> 是非管理员用户并遵循相同的程序。
B
知道A
是管理员用户并且知道它是userID
和userName
。这很有可能,没有敏感信息。
JWT 只有 Base64 编码的声明,如果客户端也知道 secret p@$$w0rd
,则客户端可以轻松生成令牌。正如我们所知,验证器 server
仅重新散列编码的 JWT(来自客户端)以匹配它使用密钥发送的 upon login
。
通过https
,我们可以确定第三者或中间人无法知道这个秘密或任何其他信息,所以我们把它放在一边。
#1
B
作为恶意用户修改了自己的令牌并将角色更改为admin
的角色,并且只允许管理员用户进行 API 调用。
Server
可以轻松地使此令牌无效,因为重新散列将失败,因为发给B
的原始令牌已被修改,并且当我们修改令牌时,签名也会更改,因为它也是由有效负载组成的。
#2
B
是一个恶意用户创建一个令牌来匹配A
的所有A
s 详细信息,并且只允许管理员用户发出 API 请求。
server
将成功验证该令牌并知道它是A
。
如何预防?
我们是否应该使用 id
声明作为唯一且
不能轻易猜到?由于这个B
无法派生
正确的声明集以创建确切的 A
s 令牌。虽然
这种方法更多地涉及存储这个额外的 ID
每个用户并在服务器上进行身份验证。
我们是否应该永远不要泄露用于签署 JWT 的 secret
密钥,所以
客户端可以创建令牌吗?
我们知道,与 Basic Authorization
相比,JWT 无疑是一种更好的身份验证方式,Basic Authorization
会在每个 API 请求中发送用户的 Base64 编码 password
,因为它具有更大的攻击窗口。
【问题讨论】:
【参考方案1】:选项 #2 - 如果从不使用对称密钥,如果客户端以任何方式不安全,尤其是当客户端是 Web 应用程序时,请永远向客户端披露它们。永远不要泄露对称密钥是个好主意。 JWT 应该在服务器上制造,即使用对称密钥预签名,然后提供给客户端。客户端可以通过某种形式的身份验证通过安全 API 请求 JWT,或者您可以创建 JWT 并通过其他方式分发给客户端。
我们两者都做。已经通过身份验证的域用户可以通过 API 调用请求过期的 JWT。域外的用户由域上可以访问 API 调用的经批准的管理员专门为他们提供 JWT。任何时候都不会暴露对称密钥。
此过程开始复制 OAuth 的某些方面,因此您可能需要调查 OAuth 服务器/供应商,这就是我们要去的地方。
【讨论】:
不要不同意你的观点@programmerj,我也不会向客户透露对称密钥。另一方面,非对称密钥的使用将比对称密钥更昂贵,因为验证过程将花费更长的时间,并且每个 API 请求都会发生这种情况,可能会导致性能问题。但是,如果我们使用不可猜测的唯一id
作为对令牌的声明,这样它就不能轻易地由某人生成呢?
我想我没有完全理解您的担忧。如果对称密钥永远不会给出,那么即使有人复制了用户的 JWT 标头和有效负载,他们也无法生成签名,因此 JWT 永远不会被服务器验证。如果有人窃取了整个有效的 JWT,那么过期声明应该会解决这个问题。使用“不可猜测的唯一 ID”本质上是“默默无闻的安全性”,通常不是一个好主意。您提到的场景已由安全专家解决,因此我再次向您指出 OAuth 或其他行业标准以获得答案。
使用 OAuth 比使用 JWT 更复杂一些,而且它们更容易设置和使用。我认为对于中型项目,使用它们不会有太大的危害。
您可以使用 JWT 作为您的授权令牌,无需 OAuth;我现在正在这样做。 OAuth 只是规定了获取/管理 JWT 的过程。项目的大小无关紧要;它的曝光范围和妥协的后果。以上是关于JSON Web Tokens 的正确使用的主要内容,如果未能解决你的问题,请参考以下文章