首页 > 解决方案 > 特定于资源的 OAuth2 授权的常见做法?

问题描述

看OAuth 2的授权码流程.....

假设用户有多个资源(例如帐户、存储库)。

客户端应该如何指定它请求权限的资源?

当然,始终由用户来选择哪个资源,但这可能会造成混淆,并且用户可能会选择错误的资源。您也可以只授予对所有资源的访问权限,但在这种情况下过于宽泛。

客户端如何通知它正在请求访问哪个资源?

例如,

https://example.com/oauth/authorize?account_id=123

对此有最佳/常见做法吗?


编辑:考虑一个 git 托管服务。

用户可以访问 repo-a 和 repo-b。

客户想要请求访问 repo-a。

应该如何构建 OAuth 以允许客户端请求访问 repo-a?(用户会拒绝访问 repo-b 的请求。)

标签: oauth-2.0

解决方案


概述

在 OAuth 中,要求用户授予对单个资源的访问权限并不常见,而您通常会进行分类,从而使资源能够增长:

  • 要求用户同意读取所有存储库的访问权限
  • 要求用户同意读取移动应用程序的所有存储库的访问权限
  • 要求用户同意读取所有 Typescript 存储库的访问权限

范围

客户端根据数据区域发送范围,以及可以使用该数据做什么:

authorize?scope='openid profile repo mobile'

授权的结果是将访问令牌发送到 API,其中可能包括以下范围:

{
"subject": 6789245,
"scope": "openid profile repo mobile"
}
  • 如果有人试图使用访问令牌来获取 repo B(不是移动 repo)的详细信息,那么 API 的授权检查将阻止这种情况,这是基于范围的授权。

索赔

每当您想动态授权时,您都可以使用声明。如果您正在构建自己的系统,则可以根据对您有意义的任何业务逻辑,自定义令牌发行以将特定的存储库添加到访问令牌:

{
"subject": 6789245,
"scope": "openid profile repo mobile"
"repos": ["A", "C"],
}
  • 如果有人试图使用访问令牌来获取 repo B 的详细信息,API 的授权检查会阻止这种情况,这是基于声明的授权。

数据访问

但是,您通常不会像这样在令牌中包含单个资源 ID,而是由您的 API 管理它们,这将在其数据访问中排除 repo B:

select * from repo where type='mobile' and subject=6789245
  • 如果有人试图使用访问令牌来获取 repo B 的详细信息,API 的授权检查将阻止这种情况,因为它不会在过滤条件中找到。请注意,这也使用声明,以确保只有数据所有者才能获得 repo。

git 细节

当然,如果您使用的是其他人的系统,您将受限于它支持的授权选项,例如GitHub Scopes,而这些可能无法满足您的要求。因此,如果无法以所需的方式限制访问,您可能需要提示访问所有存储库。

更多信息

有关使用 OAuth 设计对资源的访问的更多信息,请参阅以下 Curity 文章:

范围文章提到Prefix Scopes获取映射到特定 ID 的运行时范围,例如transaction-1234. 这是一个相当高级的主题,通常不会在 Git 存储库场景中使用——但这种模式在开放银行中使用。


推荐阅读