keycloak中的资源,范围,权限和策略

Doc*_*val 43 permissions keycloak

我想使用Keycloak的授权系统创建一个相当简单的基于角色的访问控制系统.系统Keycloak正在替换允许我们创建一个"用户",他是一个或多个"组"的成员.在该遗留系统中,通过组成员资格(其中组被分配了权限)或直接向用户授予许可,给予用户"许可"以访问大约250个"能力"中的每一个.

我想将遗留系统映射到keycloak授权.

我应该很容易将现有系统中的每个"功能"映射到一个keycloak资源和一组keycloak范围.例如,"viewAccount"功能显然会映射到"帐户"资源和"视图"范围; 并且"viewTransaction"映射到"事务"资源......但最佳做法是创建一个"视图"范围,并在多个资源(帐户,事务等)中使用它?或者我应该创建"viewAccount"范围,"viewTransaction"范围等?

同样,我对权限有点困惑.对于资源和范围的每个实际组合,通常的做法是创建权限吗?如果有多个权限与给定的资源/范围匹配,Keycloak会做什么?我猜测Keycloak的意图是允许我配置针对资源和范围的权限矩阵,所以例如我可以获得访问"帐户"的权限和"查看"范围的权限,因此我有权限查看帐户?

我问,因为所有这些的结果似乎是我的旧"viewAccount"功能最终创建了一个"帐户"资源,具有"查看"范围和"viewAccount"权限,这似乎让我回到原来的位置.哪个好,如果是正确的.

最后,显然我需要一组策略来确定是否应该应用viewAccount.但我是对的,这意味着我需要一个用户可能属于的每个遗留组的策略吗?例如,如果我有"帮助台"角色,那么我需要一个"帮助台会员"政策,然后我可以将其添加到"viewAccount"权限中.它是否正确?

谢谢,

标记

Nir*_*han 7

我希望通过纯 HTTP 方法强制执行授权,而不使用适配器,因为 Lua 没有适配器。希望这个答案可以帮助人们寻找基于非适配器的方法。

如果您正在寻找适配器,快速入门指南是最好的起点。尤其是spring boot authz 示例

对于纯基于 HTTP 的实现:

第1步:

Keycloak Admin UI 中定义策略和权限

第2步

具有哪些 HTTP 路径属于哪些资源以及每个路径所需的范围的内部映射。这也可以保存在配置文件中。当调用特定路由时,调用 Keycloak 令牌端点以验证访问令牌的声明。

{
  "policy-enforcer": {
    "user-managed-access" : {},
    "enforcement-mode" : "ENFORCING"
    "paths": [
      {
        "path" : "/someUri/*",
        "methods" : [
          {
            "method": "GET",
            "scopes" : ["urn:app.com:scopes:view"]
          },
          {
            "method": "POST",
            "scopes" : ["urn:app.com:scopes:create"]
          }
        ]
      }
    ]
  }
}
Run Code Online (Sandbox Code Playgroud)

如果您使用的是适配器并且未指定路径或资源,则适配器将在内部从 Keycloak搜索路径和资源。

第 3 步:

使用令牌端点来获取或评估权限。您可以使用response_mode参数来获得最终决定(是否提供访问权限)或检索整个权限。

curl -X POST \
  http://${host}:${port}/auth/realms/${realm}/protocol/openid-connect/token \
  -H "Authorization: Bearer ${access_token}" \
  --data "grant_type=urn:ietf:params:oauth:grant-type:uma-ticket" \
  --data "permission=Resource A#Scope A"
Run Code Online (Sandbox Code Playgroud)

如果授权请求未映射到任何权限,403则返回 HTTP 状态代码。


And*_*ndy 5

我知道我迟到了2年多,但我想我会分享我所知道的东西,并希望减轻以后读者的痛苦。完全透明-我绝不是Keycloak / OAuth / OIDC专家,我所了解的主要是阅读文档,书籍,出色的YouTube以及使用该工具。

这篇文章将由两部分组成:

  1. 我将尽我所能回答您所有的问题
  2. 我将向您展示所有如何在Keycloak中使用策略/作用域/权限的方法,而无需部署单独的应用程序,以便更好地理解该线程中的一些核心概念。请注意,尽管这主要是为了使您入门。我正在使用Keycloak 8.0.0

第一部分

开始之前的一些术语:

  • 在Keycloak,您可以创建2种类型的权限:资源型范围为基础
  • 简而言之,为了Resource-Based获得权限,您可以将其直接应用于资源
  • 为了Scoped-Based获得许可,您可以将其应用于您的范围或范围资源。

最佳实践是仅创建一个“视图”范围,并在多种资源(帐户,交易等)中使用它吗?还是应该创建“ viewAccount”范围,“ viewTransaction”范围等?

范围代表受保护资源的一组权限。在您的情况下,您有2个资源:accounttransaction,所以我倾向于第二种方法。

从长远来看,有一个全球性的view与所有的资源相关的范围内(例如accounttransactioncustomersettlement...)作出授权很难既管理和适应安全需求的变化。

以下是一些示例,您可以查看这些示例以获得设计感

不过请注意-我并不是说您不应该跨资源共享范围。实际上,Keycloak对于资源具有相同的用途type。你可以例如既需要viewAccountviewTransaction范围,以给定的帐户下的读取一个事务(毕竟,你可能需要访问帐户查看交易)。您的要求和标准将严重影响您的设计。

对于资源和范围的每种实用组合,是否通常创建许可?

不好意思,我不太了解这个问题,因此我会比较宽泛。为了授予/拒绝访问resource,您需要:

  • 定义您的政策
  • 定义您的权限
  • 将策略应用于权限
  • 将您的权限与一个scoperesource(或两者)关联

以便政策执行生效。请参阅授权过程

如何设置所有这些完全取决于您。例如,您可以:

  • 定义单个策略,并在适当的权限下绑定每个策略。

  • 更好的是,定义单个策略,然后将所有相关策略归为一个aggregated策略(一个策略策略),然后将该聚合策略与scope-based权限相关联。您可以将该scoped-based许可权应用于资源及其所有关联范围。

  • 或者,您可以通过利用两种不同的类型进一步分解权限。您可以通过resource-based权限类型专门为您的资源创建权限,并通过权限类型单独将其他权限与范围单独关联scope-based

您有选择。

如果有多个权限匹配给定的资源/范围,Keycloak会做什么?

这取决于

  1. 资源服务器的 Decision Strategy
  2. 每个权限的 Decision Strategy
  3. 每项政策的Logic价值。

Logic值与Java的!运算符相似。可以是PositiveNegative。如果LogicPositive,则该策略的最终评估保持不变。如果为Negative,则否定的最终结果(例如,如果策略评估为false,Logic则为Negative,则它将为true)。为简单起见,我们假设Logic始终设置为Positive

Decision Strategy是我们真正要解决的问题。在Decision Strategy可以是UnanimousAffirmative。从文档中

决策策略

此配置更改了策略评估引擎基于所有评估权限的结果来决定是否应授予资源或范围的方式。肯定是指至少一个许可必须评估一个肯定的决定,才能授予对资源及其范围的访问权限。一致意味着所有权限都必须评估为肯定的决定,以便最终决定也为肯定的。例如,如果对同一资源或范围的两个权限发生冲突(其中一个权限授予访问权限,另一个权限拒绝访问),则在所选策略为肯定的情况下,将授予对资源或范围的权限。否则,对任何权限的一个拒绝也将拒绝对资源或范围的访问。

让我们使用一个示例来更好地理解上述内容。假设你有2级权限的资源,有人试图访问该资源(记住,LogicPositive所有策略)。现在:

  1. Permission One有一个Decision Strategy设置为Affirmative。它还有3个策略,它们各自对它们进行评估:
    • true
    • false
    • false

由于其中一项政策设置为truePermission One因此设置为true(肯定-仅需要设置为1 true)。

  1. Permission Two有一Decision Strategy组以Unanimous2种策略:
    • true
    • false

在这种情况下Permission Twofalse因为一个策略是错误的(一致-它们都必须是true)。

  1. 现在进行最终评估。如果资源服务器的Decision Strategy设置为Affirmative,访问该资源将被授予因为Permission Onetrue。另一方面,如果资源服务器的Decision Strategy设置为Unanimous,则访问将被拒绝。

看到:

我们将继续讨论。我将Decision Strategy 在第二部分中说明如何设置资源服务器。

因此,例如,我可以有权访问“帐户”和“查看”范围的权限,因此我将有权查看帐户?

简短的答案是肯定的。现在,让我们对此进行扩展:)

如果您具有以下情况:

  1. 资源服务器Decision Strategy设置为UnanimousAffirmative
  2. 访问account/{id}资源的权限为true
  3. 访问view范围的权限为true

您将被授予访问该帐户的权限。

  • true+ true等于或true之下。 AffirmativeUnanimous Decision Strategy

现在如果你有这个

  1. 资源服务器Decision Strategy设置为Affirmative
  2. 访问account/{id}资源的权限为true
  3. 访问view范围的权限为false

你会被授予访问权限查看的帐户。

  • true+ falsetrueAffirmative的策略。

这里的要点是,对给定资源的访问还取决于您的设置,因此请小心,因为您可能不需要第二种情况。

但是我是对的,这意味着我需要一个用户可能属于的每个旧组的策略吗?

我不确定Keycloak在2年前的表现如何,但是您可以指定一个基于组的策略,然后直接在该策略下添加所有组。您当然不需要为每个组创建一个策略。

例如,如果我具有“服务台”角色,则需要一个“服务台成员身份”策略,然后可以将其添加到“ viewAccount”权限中。它是否正确?

差不多了 您可以通过多种方式进行设置。例如,您可以:

  1. 创建您的资源(例如/account/{id}),并将其与account:view范围关联。
  2. 创建基于角色的策略helpdesk在该策略下添加角色
  3. 创建一个Scope-Based名为的权限viewAccount,并将其与绑定在一起scoperesource然后policy

我们将在第二部分中进行类似的设置。

第二部分

Keycloak有一个简洁的小工具,可让您测试所有策略。更好的是,您实际上不需要启动其他应用程序服务器并部署单独的应用程序即可正常工作。

这是我们要设置的方案:

  1. 我们将创建一个名为 stackoverflow-demo
  2. 我们将bank-api在该领域下创建一个客户
  3. 我们将/account/{id}为该客户定义一个资源
  4. account/{id}将有account:view范围
  5. 我们将bob在新领域下创建一个名为
  6. 我们也将创建三个角色:bank_telleraccount_owneruser
    • 我们不会bob与任何角色相关联。现在不需要。
  7. 我们将设置以下两个Role-Based策略:
    • bank_telleraccount_owner有权访问/account/{id}资源
    • account_owner有权使用account:view范围
    • user 无权访问资源或范围
  8. 我们将使用该Evaluate工具来查看如何授予或拒绝访问。

请原谅我,这个例子是不现实的,但我对银行业并不熟悉:)

密钥斗篷设置

下载并运行Keycloak

cd tmp
wget https://downloads.jboss.org/keycloak/8.0.0/keycloak-8.0.0.zip 
unzip keycloak-8.0.0.zip
cd keycloak-8.0.0/bin
./standalone.sh 
Run Code Online (Sandbox Code Playgroud)

创建初始管理员用户

  1. http://localhost:8080/auth
  2. 点击Administration Console链接
  3. 创建管理员用户并登录

有关更多信息,请访问入门。就我们的目的而言,以上已足够。

搭建舞台

创建一个新的领域

  1. 将鼠标悬停在域上master,然后单击Add Realm按钮。
  2. 输入stackoverflow-demo作为名称。
  3. 点击Create
  4. 现在应该在左上方说stackoverflow-demo而不是master领域。

请参阅创建新领域

创建一个新用户

  1. 点击Users左侧的链接
  2. 点击Add User按钮
  3. 输入username(例如bob
  4. 确保User Enabled已打开
  5. 请点击 Save

请参阅创建新用户

创建新角色

  1. 点击Roles链接
  2. 点击 Add Role
  3. 添加下列角色:bank_telleraccount_owneruser

同样,也没有与角色的用户联系起来。对于我们的目的,这是不需要的。

查看角色

创建一个客户

  1. 点击Clients链接
  2. 点击 Create
  3. 输入bank-apiClient ID
  4. 对于Root URL进入http://127.0.0.1:8080/bank-api
  5. 点击 Save
  6. 确保Client Protocolopenid-connect
  7. 更改Access Typeconfidential
  8. 更改Authorization EnabledOn
  9. 向下滚动并点击Save。新Authorization选项卡应显示在顶部。
  10. 单击Authorization选项卡,然后Settings
  11. 确保将Decision Strategy设置为Unanimous
    • 这是资源服务器的 Decision Strategy

看到:

创建自定义范围

  1. 点击Authorization标签
  2. 点击Authorization Scopes> Create弹出Add Scope页面
  3. 输入account:view名称,然后按Enter。

创建“查看帐户资源”

  1. 点击上面的Authorization链接
  2. 点击 Resources
  3. 点击 Create
  4. 输入View Account Resource两者的NameDisplay name
  5. 输入account/{id}URI
  6. account:viewScopes文本框中输入
  7. 请点击 Save

请参阅创建资源

建立您的政策

  1. 再次在Authorization标签下,点击Policies
  2. RoleCreate Policy下拉菜单中选择
  3. 在该Name部分中,键入Only Bank Teller and Account Owner Policy
  4. 在下Realm Roles选择bank_telleraccount_owner角色
  5. 确保将Logic其设置为Positive
  6. 请点击 Save
  7. 点击Policies链接
  8. RoleCreate Policy下拉菜单中再次选择。
  9. 这次Only Account Owner Policy用于Name
  10. Realm Roles选择下account_owner
  11. 确保将Logic其设置为Positive
  12. 请点击 Save
  13. 单击Policies顶部的链接,您现在应该看到新创建的策略。

请参阅基于角色的策略

请注意,Keycloak具有更强大的策略。请参阅管理策略

创建基于资源的权限

  1. 再次在Authorization标签下,点击Permissions
  2. 选择 Resource-Based
  3. 键入View Account Resource PermissionName
  4. ResourcesView Account Resource Permission
  5. Apply Policy选择下Only Bank Teller and Account Owner Policy
  6. 确保将Decision Strategy设置为Unanimous
  7. 请点击 Save

请参阅创建基于资源的权限

ew ...

评估基于资源的权限

  1. 再次在Authorization标签下,选择Evaluate
  2. User输入bob
  3. Roles选择下user
    • 这是我们将用户与我们创建的角色相关联的地方。
  4. Resources选择下View Account Resource,然后单击Add
  5. 单击评估。
  6. 展开View Account Resource with scopes [account:view]以查看结果,您应该看到DENY

在此处输入图片说明

  1. 这是有道理的,因为我们只允许两个角色通过来访问该资源Only Bank Teller and Account Owner Policy。让我们测试一下以确保这是真的!
  2. 单击Back评估结果上方的链接
  3. 将bob的角色更改为account_owner,然后单击Evaluate。现在,您应该看到结果为PERMIT。如果您返回并将角色更改为bank_teller

请参阅评估和测试策略

创建基于范围的权限

  1. 返回本Permissions
  2. Scope-BasedCreate Permission下拉菜单中选择此时间。
  3. 在下Name,输入View Account Scope Permission
  4. 在下Scopes,输入account:view
  5. 在下Apply Policy,输入Only Account Owner Policy
  6. 确保将Decision Strategy设置为Unanimous
  7. 请点击 Save

请参阅创建基于范围的权限

第二次试运行

评估我们的新变化

  1. 返回本Authorization
  2. 点击 Evaluate
  3. 用户应该是 bob
  4. 角色应该是 bank_teller
  5. 资源应View Account Resource点击Add
  6. 点击Evaluate,我们应该得到DENY
    • 同样,这并不奇怪,因为bank_teller可以访问,resource但不能访问scope。在这里,一个许可权评估为true,另一个许可权评估为false。鉴于资源服务器的Decision Strategy设置为Unanimous,最后的决定是DENY
  7. 单击选项卡Settings下的Authorization,然后将更Decision Strategy改为Affirmative,然后再次返回到步骤1-6。这次,最终结果应该是PERMIT(一个许可为真,因此最终决定为真)。
  8. 为了完整起见,请将资源服务器的位置Decision Strategy重新设置为Unanimous。再次返回步骤1至6,但这一次将角色设置为account_owner。这次PERMIT,鉴于account_owner可以同时访问resource和,因此最终结果还是有意义的scope

整洁:)希望这会有所帮助。

  • 您肯定正在让世界变得更美好,感谢您花时间将所有这些放在一起......您应该写一些关于所有这些的博客文章!非常有用@Andy (6认同)
  • @JWo 不客气!说实话,没有什么特别的原因。我只是让示例尽可能简单,以便任何人都可以开始使用。根据我的经验,我知道这些文档并不是最令人兴奋的内容。至于需要访问银行 API 的另一个客户端,听起来您可能正在寻找“用户管理访问权限 (UMA)”,其中资源所有者可以向请求方授予对受保护资源的访问权限(至少这是我的解释)。 (3认同)

Har*_*var 5

我知道我参加聚会有点晚了,但让我尽可能多地解释一下。

在keycloak中,我们有这样的术语:

资源:用户将访问或执行操作的对象

身份验证范围:用户可以对特定对象执行的操作

政策: 政策

权限:映射实际发生在这里

如果您不想遵循手动方式,您可以导出此 JSON 并且所有用户、资源、权限都将自动设置 bu keycloak

JSON 配置文件

现在让我们看一个场景:

在此处输入图片说明

现在我们几乎没有资源,例如:

  1. 帐户
  2. 机器人
  3. 报告

我们想要实现只有特定用户才能执行特定操作的场景。

设置 Keycloak

开创新境界

  1. 单击添加领域按钮。

在此处输入图片说明

  1. 输入test-v1作为名称。
  2. 单击创建。

在此处输入图片说明

创建新角色

  1. 点击角色
  2. 点击添加角色
  3. 创建角色“admin”、“agent”和“super_admin”

在此处输入图片说明

创建客户端

  • 单击“客户端”选项卡
  • 在客户端 ID 文本框中输入app-client
  • 点击保存
  • 再次选择并选择客户端以配置其他设置
  • 验证客户端协议是openid-connect
  • 将访问类型设置为机密
  • 将授权启用设置为开
  • 最后点击保存按钮。
  • 顶部将出现一个新的授权选项卡。
  • 选择授权选项卡,然后选择设置

检查决策策略是否设置为Unanimous。这是资源服务器策略

在此处输入图片说明

创建自定义身份验证范围

转到Authorization选项卡 选择Authorization Scopes > 并单击Create在文本中 输入scopes:create & scopes:view并保存值。

在此处输入图片说明

创建资源

  • 立即转到“资源”选项卡 > 并单击“创建”
  • 一一输入,创建以下资源res:account & res:bot & res:report
  • 对于范围文本中的所有资源,请选择我们创建的早期范围:创建范围:视图
  • 点击保存

在此处输入图片说明

创建策略

  • 再次在授权选项卡中,选择策略
  • 单击创建策略下拉列表并选择角色
  • 在名称文本框中,管理员
  • 在 Realm Roles 中选择角色Admin
  • 检查逻辑设置为正
  • 单击“保存”,对“代理”和“Super_admin”执行相同操作

在此处输入图片说明

  • 再次在授权选项卡中,选择策略
  • 单击Create Policy下拉菜单并选择Aggregated
  • 在名称文本框中,Admin 或 Super_admin 或 Agent
  • 在 Realm Roles 中选择角色Admin & Super_admin & Agent
  • 检查逻辑设置为肯定
  • 点击保存 在此处输入图片说明

创建权限

  • 再次在授权选项卡中,选择权限
  • 单击Create Permissions下拉菜单并选择Scope-Based
  • 在名称文本框中,帐户创建
  • 在资源框中,选择“资源资源:帐户”
  • 在范围选择中,范围:创建
  • 应用策略管理员
  • 我们必须根据要求为所有资源设置相同的权限在此处输入图片说明

创建用户

  • 在用户选项卡内创建一个测试用户我们不会为其分配任何角色、范围或组进行测试

让我们评估

  • 再次在 Authorization 选项卡中,选择Evaluate
  • 选择我们创建的客户端,app-client
  • 在用户中选择创建的用户,测试
  • 在角色中选择创建的用户,admin
  • 资源值,res:account
  • 点击添加按钮
  • 点击评估按钮

在此处输入图片说明

您将看到授权是允许的,因为Admin角色有权在资源帐户上执行创建查看操作。

让我们再次评估

  • 再次在 Authorization 选项卡中,选择Evaluate
  • 选择我们创建的客户端,app-client
  • 在用户中选择创建的用户,测试
  • 在角色中选择创建的用户,admin
  • 资源值,res:report
  • 范围值,范围:创建
  • 点击添加按钮
  • 点击评估按钮

在此处输入图片说明

您将看到 grant is Deny因为只有Super_Admin角色有权对资源报告执行操作创建

  • 非常感谢你有帮助!我有一个问题,如果你不介意可以使用一个 API,我会将其添加到 keycloak 的代码源中以将我的应用程序连接到它,或者我只需要使用识别提供程序 (2认同)