IdentityServer4 API 资源与 API 范围中的用户声明是什么

What are User Claims in IdentityServer4 API Resources vs. API Scopes

我已经配置了一个 IdentityServer4 实例,并已成功将其配置为 OIDC 提供商的客户端。我现在正在尝试将其设置为我的应用程序的 OIDC 提供商。我已经完成了快速入门并阅读了文档,但我正在努力寻找我的具体问题的答案。

用户声明可以在几个不同的地方指定:API 资源和 API 范围。在 API 资源上指定用户声明与在该资源的 API 范围上指定用户声明有什么区别?

我对术语的理解是:

将用户声明与 API 资源 and/or 范围相关联一定是有意义的,但我无法确定原因和方式。请提供这些声明的说明性示例以及它们在上面给出的上下文中代表的内容:GitHub API(假设,如果实际定义了 none),以及通用批量导入 API.

ApiResource 可以包含许多范围(订单、折扣、会计...)。例如,您需要一个令牌来访问 GitHub 的配置文件信息,而不是存储库等。在这种情况下,GitHub 是一个 ApiResource 并包含配置文件范围。

当用户发送令牌请求时,只需指定一些范围(不是 ApiResource),然后 IdentityServer 会检测用户想要访问的 ApiResources(从请求的范围)。

ApiResource 中的 UserClaims: 当您在 ApiResource 中指定 UserClaims 时,当用户请求令牌以访问该 ApiResource 时,那些 UserClaims 将在令牌中。

范围内没有任何 UserClaims。

添加到 Mehrdad 的回答:

我喜欢将声明视为 API 中的一个对象,其中包含用于识别和授权的字段。

一些声明将来自 OAuth 访问令牌中的内容,但声明信息也可以来自其他地方。

我的 write up 可以帮助您直观地理解这一点。

资源是一个概念,可以分为逻辑部分(范围),可以以各种方式实现。无论哪种方式,尽管这在文档中可能不是很明显,但对于 IdentityServer 来说,一个资源至少有一个范围。

为了允许客户端访问资源,必须配置客户端允许该客户端使用的范围。在示例中,作用域的名称等于资源的名称,但实际上一个资源可能有多个作用域。请注意,仅允许使用一个范围的客户端可以访问整个资源(受众),除非资源(api)根据允许的范围(范围是访问令牌的一部分作为范围声明)。

IdentityServer 的一个特点是它是一个令牌提供者,例如用于访问令牌和身份令牌。

从最后一个开始,身份令牌有两种类型。有一个 'minimal' 身份令牌(仅包含 'sub' 声明)仅在请求时与访问令牌一起颁发。并且有一个 'full' 身份令牌,可以由客户端在 UserInfo 端点请求。

对于 IdentityServer,用户声明是一种资源(身份信息)。作为旁注,在使用此信息之前应征得用户同意,因为用户拥有此信息。

并非所有用户声明都应该进入在 UserInfo 端点请求的身份令牌。为了确定应该使用哪些声明,IdentityServer 查看 Identity~ tables。基于这些 tables,RequestedClaims 集合可用于用于过滤用户声明资源的 UserInfo 上下文。

换句话说,当客户端配置为请求 'openid' 范围时,则仅包含 'sub' 声明,添加 'profile' 范围将包含基础配置文件声明(如果在 UserClaims table 中可用),配置 'email' 范围会将电子邮件也添加到身份令牌中。

访问令牌也有类似的机制。基于 ApiClaims 和 ApiScopeClaims table,RequestedClaims 集合可用于授权上下文。查看 了解更多信息。

假设您要将 'name' 声明添加到访问令牌,然后将其添加到 table 之一。查看 或者实际上是整个线程,以获取更多信息。

虽然 IdentityServer 可以向访问令牌添加各种声明,但您应该怀疑这是否是正确的方法,如 this post 中所述。

访问令牌声明的问题在于这些声明用于用户授权。但用户声明通常并不意味着用户授权。而且您不想得到一个包含所有声明的超级访问令牌。

退一步说,IdentityServer是用来配置资源保护和客户端授权的。客户端可以连接到资源(范围),但有权访问信息的是用户:来自客户端的请求总是 'on behalf of the user'。这就是为什么 'sub' 声明总是(在交互式流程中)访问令牌的一部分。此外,可以扩展 IdentityServer 来处理用户身份验证。但是,尽管在当前设计中这是可能的,但用户授权不是(或至少不再是)IdentityServer 的关注点。

IdentityServer 的创建者过去一直在考虑用户授权,并为此提出了一项单独的服务:PolicyServer。从 IdentityServer 和访问令牌中取出授权声明。

因此,为了回答您的问题,不同的 table 用于配置用于构建令牌的资源、范围、客户端和过滤器。用户声明说明了有关用户(身份)的一些信息,但在访问令牌中不存在。

对于用户授权,我可以推荐一个类似 PolicyServer 服务器的实现,结合基于资源的授权。


table 的简短摘要:

  • AspNetUserClaims - 用户信息资源

  • ApiResources - 资源名称

  • ApiScopes - 作为资源一部分的一对多作用域

  • IdentityResources - 实际上是身份的范围(例如openid配置文件)

  • IdentityClaims - 为身份令牌过滤 AspNetUserClaims

  • ApiClaims - 为访问令牌过滤 AspNetUserClaims,无论请求哪个范围

  • ApiScopeClaims - 过滤访问令牌的 AspNetUserClaims,取决于请求的范围

  • ClientClaims - 为特定客户包含的声明

  • ClientScopes - 客户端允许的范围


客户请求范围。如果省略范围,则(根据规范)所有允许的范围都被视为请求。

api 是资源(受众)的一部分。当资源具有多个范围时,需要更细粒度的客户端授权(基于范围)。

用户授权用于确定允许用户执行的操作:客户端可以连接到 api,按范围(例如日历)过滤,并且用户有权读取但不能写入事件.

虽然calendar.writecalendar.read可以是作用域,但与用户授权无关。用户可以被授权读取和写入,但由于客户端可能受到限制(例如 calendar.read),用户可能必须使用单独的客户端才能连接到资源,例如日历应用程序两者都有,电子邮件应用程序只有 calendar.read