在哪里存储通过 OAuth2 (OpenID Connect) 获得的令牌
Where to store tokens obtained through OAuth2 (OpenID Connect)
我构建了一个应用程序,该应用程序根据用户的选择使用某些身份提供程序(Auth0、FusionAuth、Azure AD、AWS Cognito)。
我正在使用授权码流程。
我遇到了存储令牌的问题。
我只想使用身份提供者来登录用户,我不需要存储用户是谁(姓名、电子邮件等)。我只需要对用户进行身份验证并确保该用户来自我可以信任的身份提供者。
所以我有 4 个问题:
- 如果我不考虑使用令牌向身份提供者发出请求,我是否需要存储令牌。
- 如果没有则转到第4题。如果是,我想知道存储它们的最佳方式是什么(使用 db 保存在 session 中,或者只是将它们作为 Header 的 accessToken 和 cookie 中的 refreshToken 发送)
- 我如何验证访问令牌,因为据我所知访问令牌可能是也可能不是 JWT。由于请求的数量,每次请求都向 IP 发出请求并不是最好的方法。
- 我是否应该使用我自己创建的一对访问和刷新令牌来验证来自前端的请求。
我最近才开始研究 OAuth2,非常感谢任何答案。
截至目前我有这个流程:
- 从前端(FE) 用户重定向到身份提供程序(IP) 以登录。
- IP 使用代码重定向到 后端(BE)。
- BE 向 IP 请求获取令牌。
- BE 验证授权是否有效(通过随机数和状态)。
- BE 使用 httpOnly 安全 cookie 中的 refreshToken 和查询中的 accessToken 将用户重定向到 FE 以将其存储在 localStorage 中。
- 当 FE 向 BE 发出请求时,我使用 jwks 验证 accessToken(JWT)。
在 OAuth 中,您通常不必实施管道来构建您自己的令牌存储。例如,令牌可以仅存储在高度加密的 HTTP SameSite=strict
cookie 中。但是,您必须保持在 cookie 大小限制之内。最好的方法是向 Internet 客户端发布不透明的令牌(例如 UUID)。 Phantom Token Pattern 对此有更多信息。
您不应在自己的 API 中使用外部访问令牌。正如您发现的那样,您可能无法验证它们。此外,它们将没有有意义的 scopes and claims,并且您将无法正确授权 API 请求。而是为您自己的 API 发行您自己的代币。
授权服务器
可以在代码中发行自己的代币,但不推荐这样做。相反,首选选项是使用授权服务器。一种选择是 Curity Identity Server.
的免费社区版
此组件将为您处理与 Identity Providers 的连接。然后它会为您颁发令牌,这样您的应用程序和 API 只会处理来自单个提供商的令牌。
我构建了一个应用程序,该应用程序根据用户的选择使用某些身份提供程序(Auth0、FusionAuth、Azure AD、AWS Cognito)。
我正在使用授权码流程。 我遇到了存储令牌的问题。 我只想使用身份提供者来登录用户,我不需要存储用户是谁(姓名、电子邮件等)。我只需要对用户进行身份验证并确保该用户来自我可以信任的身份提供者。
所以我有 4 个问题:
- 如果我不考虑使用令牌向身份提供者发出请求,我是否需要存储令牌。
- 如果没有则转到第4题。如果是,我想知道存储它们的最佳方式是什么(使用 db 保存在 session 中,或者只是将它们作为 Header 的 accessToken 和 cookie 中的 refreshToken 发送)
- 我如何验证访问令牌,因为据我所知访问令牌可能是也可能不是 JWT。由于请求的数量,每次请求都向 IP 发出请求并不是最好的方法。
- 我是否应该使用我自己创建的一对访问和刷新令牌来验证来自前端的请求。
我最近才开始研究 OAuth2,非常感谢任何答案。
截至目前我有这个流程:
- 从前端(FE) 用户重定向到身份提供程序(IP) 以登录。
- IP 使用代码重定向到 后端(BE)。
- BE 向 IP 请求获取令牌。
- BE 验证授权是否有效(通过随机数和状态)。
- BE 使用 httpOnly 安全 cookie 中的 refreshToken 和查询中的 accessToken 将用户重定向到 FE 以将其存储在 localStorage 中。
- 当 FE 向 BE 发出请求时,我使用 jwks 验证 accessToken(JWT)。
在 OAuth 中,您通常不必实施管道来构建您自己的令牌存储。例如,令牌可以仅存储在高度加密的 HTTP
SameSite=strict
cookie 中。但是,您必须保持在 cookie 大小限制之内。最好的方法是向 Internet 客户端发布不透明的令牌(例如 UUID)。 Phantom Token Pattern 对此有更多信息。您不应在自己的 API 中使用外部访问令牌。正如您发现的那样,您可能无法验证它们。此外,它们将没有有意义的 scopes and claims,并且您将无法正确授权 API 请求。而是为您自己的 API 发行您自己的代币。
授权服务器
可以在代码中发行自己的代币,但不推荐这样做。相反,首选选项是使用授权服务器。一种选择是 Curity Identity Server.
的免费社区版此组件将为您处理与 Identity Providers 的连接。然后它会为您颁发令牌,这样您的应用程序和 API 只会处理来自单个提供商的令牌。