"刷新令牌"的目的是什么?

Jas*_*rod 33 authentication oauth youtube-api access-token refresh-token

我有一个与YouTube直播API集成的程序.它运行在计时器上,因此我可以通过刷新令牌每隔50分钟编程一次获取新的访问令牌.我的问题是,为什么?

当我通过YouTube验证时,它给了我一个刷新令牌.然后,我使用此刷新令牌大约每小时获取一个新的访问令牌.如果我有刷新令牌,我总是可以使用它来获得一个新的访问令牌,因为它永远不会过期.所以我不知道这是多么安全,而不仅仅是从一开始就给我一个访问令牌,而不是整个刷新令牌系统.

Tey*_*yam 44

基本上,刷新令牌用于获取新的访问令牌.

为了清楚地区分这两个令牌并避免混淆,这里是他们在OAuth 2.0授权框架中给出的功能:

  • 授权服务器在资源所有者的批准下向第三方客户端颁发访问令牌.客户端使用访问令牌来访问资源服务器托管的受保护资源.
  • 刷新令牌是用于获取访问令牌的凭据.刷新令牌由授权服务器发布给客户端,用于在当前访问令牌失效或过期时获取新的访问令牌,或者获取具有相同或更窄范围的其他访问令牌.

现在,为了回答你为何仍然被发出刷新令牌而不仅仅是保护访问令牌的问题,互联网工程任务组在刷新令牌中提供的主要原因是:

有一个安全原因,refresh_token它只与授权服务器交换,而access_token与资源服务器交换.这样可以减少长时间访问权限泄露的风险,即"一小时内的访问权限令牌,一年内刷新令牌有效,或者直到被撤销"与"无法刷新的访问令牌直至撤销"令牌".

有关OAuth 2.0 Flow的更详细和完整信息,请尝试浏览以下参考:

  • 为什么不在过期时获取新的短期 access_token 呢?如果您无论如何都需要向服务器请求新的access_token,为什么还要拥有长期存在的refresh_token?或者,使用refresh_token,我不需要维护活动的身份提供者cookie,并且即使在cookie早已消失之后,它也会根据refresh_token发出新的access_token,并且如果用户想要获得a,则必须输入他的凭据新的访问令牌? (11认同)
  • 刷新令牌也应该有助于获取新的刷新令牌吗? (9认同)
  • 这个答案主要关注“什么”,而很少关注“为什么”。我认为一个现实世界的例子会让读者受益。 (7认同)
  • @JustAMartin作为OAuth2客户端,如果没有刷新令牌,我需要再次启动整个授权流程(让用户“登录”并再次授予我权限),以便获得另一个访问令牌。刷新令牌绕过此要求,作为一种“证明”,证明我作为客户端已收到用户请求访问令牌的许可。 (6认同)
  • @Sammy Taylor 完全同意。我不敢相信我读了整面墙的文字却一无所获 (3认同)

Den*_*sel 37

以下是OAuth 2.0 文档中的信息。

刷新令牌用于在当前访问令牌无效或过期时获取新的访问令牌,或者获取具有相同或更窄范围的其他访问令牌(访问令牌的生命周期可能比资源所有者授权的更短,权限也更少)。

  +--------+                                           +---------------+
  |        |--(A)------- Authorization Grant --------->|               |
  |        |                                           |               |
  |        |<-(B)----------- Access Token -------------|               |
  |        |               & Refresh Token             |               |
  |        |                                           |               |
  |        |                            +----------+   |               |
  |        |--(C)---- Access Token ---->|          |   |               |
  |        |                            |          |   |               |
  |        |<-(D)- Protected Resource --| Resource |   | Authorization |
  | Client |                            |  Server  |   |     Server    |
  |        |--(E)---- Access Token ---->|          |   |               |
  |        |                            |          |   |               |
  |        |<-(F)- Invalid Token Error -|          |   |               |
  |        |                            +----------+   |               |
  |        |                                           |               |
  |        |--(G)----------- Refresh Token ----------->|               |
  |        |                                           |               |
  |        |<-(H)----------- Access Token -------------|               |
  +--------+           & Optional Refresh Token        +---------------+
Run Code Online (Sandbox Code Playgroud)

(A) 客户端通过向授权服务器进行身份验证并提供授权许可来请求访问令牌。

(B) 授权服务器对客户端进行身份验证并验证授权授予,如果有效,则颁发访问令牌和刷新令牌。

(C) 客户端通过出示访问令牌向资源服务器发出受保护的资源请求。

(D) 资源服务器验证访问令牌,如果有效,则为请求提供服务。

(E) 重复步骤 (C) 和 (D),直到访问令牌过期。如果客户端知道访问令牌已过期,则跳至步骤(G);否则,它会发出另一个受保护的资源请求。

(F) 由于访问令牌无效,资源服务器返回无效令牌错误。

(G) 客户端通过向授权服务器进行身份验证并提供刷新令牌来请求新的访问令牌。客户端身份验证要求基于客户端类型和授权服务器策略。

(H) 授权服务器对客户端进行身份验证并验证刷新令牌,如果有效,则颁发新的访问令牌(以及可选的新刷新令牌)。

  • 我对最后一步有疑问。使用刷新令牌发送刷新令牌是不好的做法吗?我不应该这样做吗? (2认同)

jra*_*ali 36

刷新令牌至少有两个用途。首先,刷新令牌是一种“证明”,表明 OAuth2 客户端已经从用户那里获得了访问其数据的许可,因此可以再次请求新的访问令牌,而无需用户通过整个 OAuth2 流程。其次,与长期访问令牌相比,它有助于增加整个安全流程。我将更详细地讨论这两点。

刷新令牌作为不惹恼用户的一种方式

让我们用一个例子来谈谈第一个目的。假设您是一名用户,正在使用想要与您的 YouTube 帐户数据进行交互的第三方客户端网络应用程序。一旦授予权限的客户端应用程序使用YouTube的数据,你会希望客户端应用程序提示您输入您的许可,再次它的 YouTube 令牌何时过期?如果 YouTube 令牌的到期时间非常短,例如 5 分钟,会发生什么情况。如果客户端应用程序至少每 5 分钟提示您一次许可,那会有点烦人!OAuth2 针对这个“问题”提出的解决方案是刷新令牌。通过使用刷新令牌,访问令牌可以保持短暂的生命周期(这在访问令牌以某种方式泄露或被盗的情况下是可取的),并且刷新令牌可以保持长期(更)生命周期,从而允许客户端获得新的访问权限令牌过期时无需用户许可(再次)。

但是为什么要刷新令牌呢?如果重点是不让用户收到权限请求,那么为什么客户端不能简单地说“嘿,授权服务器,我想要另一个访问令牌。现在!”?或者,“嘿授权服务器,这是我过期的令牌,给我一个新的!”。嗯,刷新令牌作为一种“证明”,证明客户端在某个原始时间点被用户授予访问权限。该“证明”采用由授权服务器数字签名的刷新令牌的形式。通过客户端提供刷新令牌,授权服务器可以验证客户端在过去的某个时间点收到了用户的许可,并且客户端不必再次提示用户。

刷新令牌作为提高安全性的一种手段

然而,这提出了一个问题,“好吧,如果刷新令牌被泄露或被盗,或者只是被恶意客户端应用程序保留而没有应用户的要求将其删除,会发生什么?攻击者不能继续使用刷新令牌无限期地(或直到它过期)获得有效的访问令牌?这个问题导致讨论我提到的第二个目的,刷新令牌有助于更安全的流程。

访问令牌出现的问题是,一旦获得,它们只会呈现给资源服务器(例如 YouTube)。因此,如果访问令牌被盗或泄露,您如何告诉资源服务器不要信任该令牌?好吧,你真的不能。唯一的方法是更改​​授权服务器上的私有签名密钥(首先对令牌进行签名的密钥)。我想这样做不方便,并且在某些情况下(例如 Auth0)不受支持。

另一方面,刷新令牌需要频繁地提交给授权服务器,因此如果一个令牌被泄露,那么撤销或拒绝整个刷新令牌是微不足道的,而不必更改任何签名密钥。

  • 意思是不惹恼用户为我解释这一点。在我的上下文中,我从 Web 后端访问 API,因此我永远不需要手动输入凭据,它们在应用程序中可用。我一直想知道,为什么不每次使用我的凭据获取一个新令牌,为什么存储刷新令牌并跟踪其过期时间。我从未想过在手动输入凭据的用户工作流程中这会非常烦人。 (4认同)
  • @jmrah根据您发布的答案,如果在某种情况下**资源服务器**和**授权服务器**相同(我的意思是,例如,一个提供资源并且也做授权本身),使用**刷新令牌**是否**没有**那么有意义? (4认同)

小智 33

仅使用Access Token比同时使用Access TokenRefresh Token 的风险要大得多。

例如,您仅使用Access Token设置“100 天”到期日,但有一天,Access Token被黑客窃取。现在,黑客有很大机会可以自由使用访问令牌,最长期限为 100 天,用于不良目的。

现在,您同时使用访问令牌设置“60 分钟”到期日期刷新令牌设置“100 天”到期日期,但有一天,访问令牌被黑客窃取。现在,黑客自由使用访问令牌用于不良目的的机会要小得多,最多 60 分钟。

现在,您会想到刷新令牌是否被盗了。实际上,如果刷新令牌被黑客盗取,黑客仍然有很大的机会可以自由使用刷新令牌,最长期限为 100 天,用于不良目的。但Refresh Token被盗的概率远小于Access Token被盗的概率,因为Refresh Token每 60 分钟才使用一次来刷新Access Token(获取新的 Access Token),而Access Token是在每次访问资源时使用的,更频繁。

因此,您最好同时使用Access TokenRefresh Token


Lah*_*ima 19

access_tokens 使用更频繁,并且撤销能力并不是很重要,因为它们的寿命很短。

refresh_tokens 的使用频率较低,并且撤销的能力至关重要,因为它们可用于生成新的access_tokens。

验证签名令牌的成本较低,但撤销很困难。

验证存储在数据库中的令牌成本高昂,但可以轻松撤销。

因此,签名密钥可以用作access_tokens 来提高性能。

Db 存储的密钥可以用作refresh_tokens,以便轻松撤销它们。

如果没有refresh_token,就很难找到一种提供低成本验证和轻松撤销能力的机制。refresh_token由于性能原因所以存在。


小智 11

“所以我不认为这比从一开始就给我一个访问令牌而不打扰整个刷新令牌系统更安全。” 我在同样的问题上挣扎。简短的回答是刷新令牌是确保凭据未过期所必需的。

一个例子可能会有所帮助:我有一个存储您的医疗记录的数据库。您同意与您的配偶分享您的医疗记录。您的配偶使用他们的访问令牌从我的数据库中读取您的记录。两周后,您的配偶再次检查您的医疗记录,刷新令牌用于确保他们仍然有权(来自身份验证服务器)查看您的记录。刷新令牌绕过了您的配偶向身份验证服务器重新输入其凭据(用户名和密码)的需要,但它确实确保他们仍然具有访问资源的合法性。永不过期的访问令牌不会知道您是否撤销了您的配偶访问您的医疗记录的权利。

  • 如果我撤销了配偶访问我的医疗记录的权利,即使访问令牌永不过期,访问令牌是否也会无效? (2认同)

Kla*_*ven 11

拥有短期访问令牌和长期刷新令牌至少有 3 个有些相关的原因。

不记名代币

从原来的问题来看:

如果我有刷新令牌,我总是可以使用它来获取新的访问令牌,因为它永远不会过期。

尽管始终能够使用刷新令牌获取新的访问令牌,但攻击者通常可能无法获取。这是因为您对刷新令牌的使用与您作为客户端的身份证明相结合,例如通过提供您的 client_secret。访问令牌不需要此类证明,访问令牌是不记名令牌,即只需提供它们就足够了。

让访问令牌是短暂的会在一定程度上减轻访问令牌原本无限的权力。

攻击面

访问令牌与(可能许多)资源服务器交换,这增加了泄漏的机会。刷新令牌仅与授权服务器交换。

同样,访问令牌的短暂性至少是某种程度的缓解措施。

撤销

将访问令牌实现为签名的 JWT 是可能的(并且很常见)。在这种情况下,任何服务器(知道签名方的公钥,通常位于某个众所周知的位置)都可以独立验证访问令牌的正确性。这允许很好地解耦架构,从某种意义上说,资源服务器不必向授权服务器询问授权。

这种设置的缺点是无法撤销此类令牌(无需像撤销授权服务器的公钥那样剧烈的操作)。

通过使访问令牌的生命周期较短,可以简单地允许它们用完而不是明确地撤销。


xme*_*eko 5

@Teyam提及SO post为什么OAuth v2同时具有访问令牌和刷新令牌?但我更喜欢那里的另一个答案:https : //stackoverflow.com/a/12885823/254109

TL; DR refresh_token不会带来更高的安全性。目的是提高可伸缩性和性能。然后,access_token可能只是存储在一些快速的临时存储(如内存)中。它还允许授权和资源服务器分离。

  • 除了@Teyam 提到的安全原因:“refresh_token 只与授权服务器交换,而 access_token 与资源服务器交换” (7认同)
  • 只有当我们假设授权服务器在某种程度上比资源服务器更安全时,这才更安全。如果不是这种情况,它实际上不太安全。如果刷新令牌被泄露,我可以使用它来获取新的访问令牌。 (4认同)
  • 长话短说;博士?是不是真的 ? (3认同)