如何使用 oAuth2 对 SPA 用户进行身份验证? [英] How to authenticate SPA users using oAuth2?

查看:47
本文介绍了如何使用 oAuth2 对 SPA 用户进行身份验证?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

好的,我已经花了几天时间寻找有关如何在使用 SPA 时正确验证用户身份的正确解决方案.

Alright, I've spent several days looking for a proper solution on how to properly authenticate users when working with SPAs.

  1. 我有自己的网站.
  2. 我有自己的 API.
  3. 我有自己的单页应用程序.
  4. 我有自己的用户数据库.

目标:我需要通过提供用户名和密码来获取 access_token.

我查看了 OAuth2 隐式授权,但它要求用户在身份验证成功后批准/拒绝应用程序.因为我拥有应用程序和 API,所以它在我的情况下不起作用.

I looked at OAuth2 Implicit Grant, but it requires users to Approve/Decline the app after successful authentication. It doesn't work in my case since I own both the app and the API.

我查看了 OAuth2 密码授予,这并不完美,因为我需要公开 client_id/client_secret.

I looked at OAuth2 Password Grant, which is not perfect since I need to expose client_id/client_secret.

我关注 OAuth2 的原因是 API 最终会公开.

The reason I'm looking at OAuth2 is because the API will eventually be public.

是否有标准的方法来做到这一点?我目前的选择:

Is there a standard way of doing this? My current options:

  1. 忘记 OAuth2 并在用户 POST 用户名/密码时手动生成 access_token(在这种情况下,我必须在 API 公开时引入 OAuth2)
  2. 使用 OAuth2 Password Grant 并在服务器上注入 client_id/client_secret,以便让客户端应用程序非常简单(也避免所有那些 dev/staging/prod client_id/client_secret 对)

推荐答案

隐式授权

您是对的,隐式授权类型看起来不合适.但是我认为您不赞成它的原因是不正确的,因为批准步骤不是强制性的,并且在 Spring OAuth 2 实现中(我不知道您使用的是哪个实现),您可以将授权服务器配置为自动批准授权请求,以便跳过审批步骤.

Implicit Grant

You are right that Implicit grant type does not look appropriate. But I think your reason for not favoring it is incorrect because the approval step is not mandatory and in Spring OAuth 2 implementation (I don't know which implementation you are using) you can configure the Authorization server to auto approve authorization requests so that the approval step is skipped.

我认为隐式流程"的原因不合适的是

The reasons I think the "Implicit flow" is not suitable are

  1. 缺少提供客户端密码和授权代码的客户端身份验证步骤.所以安全性较低.
  2. 访问令牌作为 URL 片段发送回(这样令牌不会转到服务器),它将继续保留在浏览器历史记录中
  3. 如果发生 XSS 攻击,恶意脚本可以很好地将令牌发送到远程服务器

资源所有者密码凭据授予

如果授权服务器和资源服务器是一样的,我认为这是一种快速启动和运行的方式.RFC 6749 在第 4.3.2 节中说:

Resource Owner Password Credentials Grant

If the authorization server and the resource server are the same, I think this is a quick way of getting up and running. RFC 6749 in Section 4.3.2 says:

如果客户端类型是机密的,或者客户端获得了客户端凭据(或分配了其他身份验证要求),则客户端必须按照第 3.2.1 节所述向授权服务器进行身份验证.

If the client type is confidential or the client was issued client credentials (or assigned other authentication requirements), the client MUST authenticate with the authorization server as described in Section 3.2.1.

这意味着此处不强制使用客户端密钥进行客户端身份验证.现在,对于授权代码授予类型,我们需要客户端机密,因为用户直接向授权服务器提供他/她的凭据,然后当客户端请求访问令牌时,除了客户端机密之外,它没有其他任何东西向授权服务器证明这是一个真实的请求.

This means that the client authentication with client secret is not mandatory here. Now, for authorization code grant type, we need the client secret because the user provides his/her credentials directly to the authorization server and then when the client requests for the access token, it doesn;t have anything else other than the client secret to prove to the authorization server that this is a genuine request.

但在资源所有者密码凭据授予类型的情况下,用户已将其凭据提供给客户端本身,然后客户端将发送这些相同的用户凭据以请求访问令牌.因此,访问令牌请求只能使用用户凭据进行身份验证,如果我们不在这里提供客户端机密,我认为我们在安全方面不会有任何损失.

But in case of resource owner password credential grant type, the user has provided its credentials to the client itself and the client will then send these same user credentials for requesting access token. Therefore, the access-token request can be authenticated with the user credentials only and if we don't provide a client secret here, I don't think we are losing anything in terms of security.

因此,您绝对可以在 SPA 中使用密码凭据授予类型.

So, you can definitely use password credential grant type in your SPA.

我认为这应该是首选选项,前提是客户端机密未存储在浏览器中.在用户身份验证(以及可选的用户批准)之后,授权服务器可以使用 URL 中的授权代码将浏览器重定向到服务器端端点.服务器端端点将使用授权码、客户端 ID 和客户端密码(仅存储在服务器端)来请求访问令牌.一旦访问令牌可用,服务器端端点就可以将用户重定向(HTTP 响应代码 302)到带有用于 CSRF 保护和访问令牌的适当 cookie 的 SPA URL.因此,我们不会在浏览器中存储客户端机密.

I think this should be the preferred option provided the client secret is not stored in the browser. After user authentication (and optionally user approval), the authorization server can redirect the browser to a server side endpoint with the authorization code in the URL. The server side end point will the request for the access token using the authorization code, client id and client secret (which is stored in the server side only). Once the access token is available, the server side endpoint can redirect (HTTP response code 302) the user to the SPA URL with appropriate cookies for CSRF protection and access token. Thus we are not storing the client secret in the browser.

通过使用授权码授予类型,您基本上可以使解决方案更加安全和通用.将来,如果您想使用不同的 SPA 进行单点登录,您可以通过重用与身份验证数据库(最好是 LDAP 服务器)集成的相同授权服务器轻松实现.

By using authorization code grant type, you are basically making the solution more secured and generic. In future, if you want to do a single sign-on with a different SPA, you can do that easily by reusing the same authorization server with its integration with the authentication database (preferably an LDAP server).

有关详细信息,请参阅我的此处为 StackOverflow 的答案.

For further details, refer to my StackOverflow answer here.

这篇关于如何使用 oAuth2 对 SPA 用户进行身份验证?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆