Amazon OpenSearch Service 中的 Identity and Access Management - Amazon OpenSearch Service

Amazon OpenSearch Service 中的 Identity and Access Management

Amazon OpenSearch Service 提供了多种方式来控制对域的访问。本主题介绍了各种策略类型,其彼此交互的方式,以及如何创建您自己的自定义策略。

重要

VPC 支持为 OpenSearch Service 访问控制引入了一些其他注意事项。有关更多信息,请参阅 关于 VPC 域的访问策略

策略的类型

OpenSearch Service 支持三种类型的访问策略:

基于资源的策略

您可以在创建域时添加基于资源的策略(通常称为域访问策略)。这些策略指定主体可以对域的子资源执行哪些操作(跨集群搜索除外)。子资源包括 OpenSearch 索引和 API。Principal 元素指定账户、用户或允许访问的角色。Resource 元素指定这些委托人可以访问哪些子资源。

例如,以下基于资源的策略将授予 test-user 针对 test-domain 上的子资源的完全访问权限 (es:*):

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::123456789012:user/test-user" ] }, "Action": [ "es:*" ], "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/*" } ] }

两个重要注意事项适用于此策略:

  • 这些权限仅适用于此域。除非您在其他域上创建类似的策略,否则 test-user 只能访问 test-domain

  • Resource 元素中的尾随 /* 非常重要,并表示基于资源的策略仅适用于域的子资源,而不适用于域本身。在基于资源的策略中,es:* 操作等同于 es:ESHttp*

    例如,test-user 可以向索引 (GET https://search-test-domain.us-west-1.es.amazonaws.com/test-index) 发送请求,但不可以更新域的配置 (POST https://es.us-west-1.amazonaws.com/2021-01-01/opensearch/domain/test-domain/config)。注意两个终端节点之间的差异。访问配置 API 需要一个基于身份的策略

您可以通过添加通配符来指定部分索引名称。此示例将识别任何以 commerce 开头的索引:

arn:aws:es:us-west-1:987654321098:domain/test-domain/commerce*

在这种情况下,该通配符意味着 test-user 可以请求 test-domain 中名称以 commerce 开头的索引。

要进一步限制 test-user,您可以应用以下策略:

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::123456789012:user/test-user" ] }, "Action": [ "es:ESHttpGet" ], "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/commerce-data/_search" } ] }

现在,test-user 只能执行一项操作:搜索 commerce-data 索引。域中的所有其他索引均不可访问,且如果没有使用 es:ESHttpPutes:ESHttpPost 操作的权限,test-user 将无法添加或修改文档。

接下来,您可以决定为高级用户配置角色。此策略提供对索引中所有 URI 的 HTTP GET 和 PUT 方法的 power-user-role 访问权限:

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::123456789012:role/power-user-role" ] }, "Action": [ "es:ESHttpGet", "es:ESHttpPut" ], "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/commerce-data/*" } ] }

如果您的域位于 VPC 中或使用精细访问控制,您可以使用开放域访问策略。否则,您的域访问策略必须包含一些限制,无论是按委托人还是按 IP 地址。

有关所有可用操作的信息,请参阅策略元素参考。要对数据进行更精细的控制,请使用具有精细访问控制权限的开放域访问策略。

基于身份的策略

与基于资源的策略(作为每个 OpenSearch Service 域的一部分)不同,您使用 AWS Identity and Access Management (IAM) 服务将基于身份的策略附加到用户或角色。与基于资源的策略一样,基于身份的策略指定谁可以访问服务,他们可以执行哪些操作,以及他们可以对哪些资源执行这些操作(如果适用)。

虽然不一定,但基于身份的策略往往更通用。它们通常仅控制用户可执行的配置 API 操作。准备好这些策略后,您可以在 OpenSearch Service 中使用基于资源的策略(或精细访问控制)为用户提供对 OpenSearch 索引和 API 的访问权限。

注意

具有 AWS 托管的 AmazonOpenSearchServiceReadOnlyAccess 策略的用户无法查看控制台上的集群运行状况。要允许它们查看集群运行状况(和其他 OpenSearch 数据),请向访问策略添加 es:ESHttpGet 操作并将该操作附加到其账户或角色。

由于基于身份的策略附加到用户或角色 (委托人),JSON 不会指定委托人。以下策略授予对以 DescribeList 开头的操作的访问权限。这种操作组合提供对域配置的只读访问权限,但不提供对域本身中存储的数据的访问权限:

{ "Version": "2012-10-17", "Statement": [ { "Action": [ "es:Describe*", "es:List*" ], "Effect": "Allow", "Resource": "*" } ] }

管理员可能对 OpenSearch Service 以及所有域上存储的所有数据拥有完全访问权限:

{ "Version": "2012-10-17", "Statement": [ { "Action": [ "es:*" ], "Effect": "Allow", "Resource": "*" } ] }

借助基于身份的策略,您可以使用标签来控制对配置 API 的访问。例如,如果域具有 team:devops 标签,以下策略允许附加的委托人查看和更新域的配置:

{ "Version": "2012-10-17", "Statement": [{ "Action": [ "es:UpdateDomainConfig", "es:DescribeDomain", "es:DescribeDomainConfig" ], "Effect": "Allow", "Resource": "*", "Condition": { "ForAnyValue:StringEquals": { "aws:ResourceTag/team": [ "devops" ] } } }] }

您还可以使用标签来控制对 OpenSearch API 的访问。OpenSearch API 基于标签的策略仅适用于 HTTP 方法。例如,如果域具有 environment:production 标签,则以下策略允许附加的主体向 OpenSearch API 发送 GET 和 PUT 请求:

{ "Version": "2012-10-17", "Statement": [{ "Action": [ "es:ESHttpGet", "es:ESHttpPut" ], "Effect": "Allow", "Resource": "*", "Condition": { "ForAnyValue:StringEquals": { "aws:ResourceTag/environment": [ "production" ] } } }] }

要更精细地控制 OpenSearch API,请考虑使用精细的访问权限控制

注意

在将一个或多个 OpenSearch API 添加到任何基于标签的策略之后,必须执行一个标签操作(例如添加、删除或修改标签),以使更改在域中生效。您必须使用服务软件 R20211203 或更高版本,才能在基于标签的策略中包含 OpenSearch API 操作。

OpenSearch Service 支持配置 API(但不是 OpenSearch API)的 RequestTagTagKeys 全局条件键。这些条件仅适用于在请求中包含标签的 API 调用,例如 CreateDomainAddTagsRemoveTags。以下策略允许附加的委托人创建域,但仅当它们在请求中包含team:it 标签时:

{ "Version": "2012-10-17", "Statement": { "Effect": "Allow", "Action": [ "es:CreateDomain", "es:AddTags" ], "Resource": "*", "Condition": { "StringEquals": { "aws:RequestTag/team": [ "it" ] } } } }

有关使用标签进行访问控制的更多详细信息,以及基于资源的策略和基于身份的策略之间的差异,请参阅 IAM 用户指南

基于 IP 的策略

基于 IP 的策略将对域的访问限制在一个或多个 IP 地址或 CIDR 块。从技术上讲,基于 IP 的策略不是一种不同类型的策略。相反,它们仅仅是指定匿名委托人的基于资源的策略,且包含一个特殊的 Condition 元素。

基于 IP 的策略的主要吸引力在于,它们允许对 OpenSearch Service 域发送未签名请求,这可让您使用 curlOpenSearch 控制面板等客户端或通过代理服务器访问域。要了解更多信息,请参阅 使用代理从 OpenSearch 控制面板访问 OpenSearch Service

注意

如果您为您的域启用了 VPC 访问,则无法配置基于 IP 的策略。但您可以使用安全组来控制哪些 IP 地址可以访问该域。有关更多信息,请参阅 关于 VPC 域的访问策略

以下策略向源自指定 IP 范围的所有 HTTP 请求授予对 test-domain 的访问权限:

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": "*" }, "Action": [ "es:ESHttp*" ], "Condition": { "IpAddress": { "aws:SourceIp": [ "192.0.2.0/24" ] } }, "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/*" } ] }

如果您的域具有公共终端节点,并且不使用精细访问控制,我们建议您将 IAM 委托人和 IP 地址结合使用。此策略仅在请求源自指定的 IP 范围时向 test-user 授予 HTTP 访问权限:

{ "Version": "2012-10-17", "Statement": [{ "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::987654321098:user/test-user" ] }, "Action": [ "es:ESHttp*" ], "Condition": { "IpAddress": { "aws:SourceIp": [ "192.0.2.0/24" ] } }, "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/*" }] }

当策略发生冲突时

当策略不一致或没有明确提到某个用户时,复杂性将提高。IAM 用户指南中的了解 IAM 的工作方式提供了策略评估逻辑的简明摘要:

  • 默认情况下,所有请求都将被拒绝。

  • 显式允许将取代此默认设置。

  • 显式拒绝将覆盖任何允许。

例如,如果某个基于资源的策略向您授予访问某个域子资源(OpenSearch 索引或 API)的权限,但一个基于身份的策略拒绝您访问,则您将被拒绝访问。如果某个基于身份的策略授予访问权限,基于资源的策略不指定您是否应具有访问权限,则您将被允许访问。请参阅以下交叉策略表,了解域子资源结果的完整摘要。

在基于资源的策略中允许 在基于资源的策略中拒绝 在基于资源的策略中既不允许也不拒绝
Allowed in identity-based policy

允许

Deny Allow
Denied in identity-based policy Deny Deny Deny
Neither allowed nor denied in identity-based policy Allow Deny Deny

策略元素参考

OpenSearch Service 支持 IAM Policy 元素参考中的大多数策略元素,但 NotPrincipal 除外。下表显示了最常用的元素。

JSON 策略元素 Summary
Version

当前版本的策略语言为 2012-10-17。所有访问策略均应指定该值。

Effect

此元素指定该语句是允许还是拒绝对特定操作的访问。有效值为 AllowDeny

Principal

此元素指定允许或拒绝访问资源的 AWS 账户 或 IAM 角色或用户,并可采用多种形式:

  • AWS 账户"Principal":{"AWS": ["123456789012"]} 或者 "Principal":{"AWS": ["arn:aws:iam::123456789012:root"]}

  • IAM 用户"Principal":{"AWS": ["arn:aws:iam::123456789012:user/test-user"]}

  • IAM 角色"Principal":{"AWS": ["arn:aws:iam::123456789012:role/test-role"]}

重要

指定 * 通配符会支持匿名访问域,我们不建议这样做,除非您添加一个基于 IP 的条件,使用 VPC 支持,或启用细粒度的访问控制。此外,还要仔细检查以下策略,来确认它们不会授予广泛访问权限:

  • 附加到关联 AWS 主体(例如 IAM 角色)的基于身份的策略

  • 附加到关联 AWS 资源(例如 AWS Key Management Service KMS 密钥)的基于资源的策略

Action

OpenSearch 服务对 OpenSearchHTTP 方法使用 ESHttp* 操作。其余操作适用于配置 API。

某些 es: 操作支持资源级权限。例如,您可以向用户授予删除一个特定域的权限,而无需向该用户授予删除任何 域的权限。其他操作仅适用于服务本身。例如,es:ListDomainNames 在单个域范围内没有意义,因此需要一个通配符。

有关所有可用操作的列表,以及它们是适用于域子资源 (test-domain/*)、域配置 (test-domain),还是仅适用于服务 (*),请参阅《服务授权参考》中的 Amazon OpenSearch Service 的操作、资源和条件键

基于资源 的策略与资源级 权限不同。基于资源的策略是附加到域的完整 JSON 策略。资源级权限可让您将操作限制于特定域或子资源。在实际工作中,您可以将资源级权限视为基于资源的策略或基于身份的策略的可选部分。

虽然 es:CreateDomain 的资源级权限可能看起来不直观—究竟为何要向用户授予创建已存在的域的权限?但通配符的使用可让您强制实施一个简单的域命名架构,例如 "Resource": "arn:aws:es:us-west-1:987654321098:domain/my-team-name-*"

当然,您完全可以在限制性较低的资源元素旁包括如下操作:

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "es:ESHttpGet", "es:DescribeDomain" ], "Resource": "*" } ] }

要了解有关配对操作和资源的更多信息,请参阅此表中的 Resource 元素。

Condition

OpenSearch Service 支持 IAM 用户指南的可用的 AWS 全局条件键中所述的大多数情况。明显的例外情况包括 aws:PrincipalTag 密钥,而 OpenSearch Service 不支持这些密钥。

配置基于 IP 的策略时,您指定 IP 地址或 CIDR 块作为条件,如下所示:

"Condition": { "IpAddress": { "aws:SourceIp": [ "192.0.2.0/32" ] } }

正如 基于身份的策略 中所述,aws:ResourceTagaws:RequestTagaws:TagKeys 条件键适用于配置 API 和 OpenSearch API。

Resource

OpenSearch Service 使用 Resource 元素的三种基本方式:

  • 对于应用于 OpenSearch Service 本身的操作(如 es:ListDomainNames),或若要允许完整访问权限,请使用以下语法:

    "Resource": "*"
  • 对于涉及域的配置的操作 (例如 es:DescribeDomain),您可以使用以下语法:

    "Resource": "arn:aws:es:region:aws-account-id:domain/domain-name"
  • 对于应用于域的子资源的操作 (例如 es:ESHttpGet),您可以使用以下语法:

    "Resource": "arn:aws:es:region:aws-account-id:domain/domain-name/*"

    您不一定要使用通配符。OpenSearch Service 可让您为每个 OpenSearch 索引或 API 定义不同的访问策略。例如,您可以限制用户对 test-index 索引的权限:

    "Resource": "arn:aws:es:region:aws-account-id:domain/domain-name/test-index"

    与对 test-index 的完全访问权限相比,您可能更愿意将策略限制在仅搜索 API:

    "Resource": "arn:aws:es:region:aws-account-id:domain/domain-name/test-index/_search"

    您甚至可以控制对单个文档的访问:

    "Resource": "arn:aws:es:region:aws-account-id:domain/domain-name/test-index/test-type/1"

    基本上,如果 OpenSearch 将子资源表示为一个 URI,则可使用访问策略控制对其进行的访问。有关对用户可访问的资源的更多控制,请参阅在 Amazon OpenSearch Service 中进行精细访问控制

有关哪些操作支持资源级权限的详细信息,请参阅此表中的 Action 元素。

高级选项和 API 注意事项

OpenSearch Service 有多个高级选项,其中一个具有访问控制影响:rest.action.multi.allow_explicit_index。在其默认设置为 true 时,它允许用户在某些情况下绕过子资源权限。

例如,请考虑以下基于资源的策略:

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::123456789012:user/test-user" ] }, "Action": [ "es:ESHttp*" ], "Resource": [ "arn:aws:es:us-west-1:987654321098:domain/test-domain/test-index/*", "arn:aws:es:us-west-1:987654321098:domain/test-domain/_bulk" ] }, { "Effect": "Allow", "Principal": { "AWS": [ "arn:aws:iam::123456789012:user/test-user" ] }, "Action": [ "es:ESHttpGet" ], "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/restricted-index/*" } ] }

此策略向 test-user 授予对 test-index 和 OpenSearch 批量 API 的完全访问权限。它还允许对 GET 发送 restricted-index 请求。

正如您可能预料的,以下索引请求将因权限错误而失败:

PUT https://search-test-domain.us-west-1.es.amazonaws.com/restricted-index/movie/1 { "title": "Your Name", "director": "Makoto Shinkai", "year": "2016" }

与索引 API 不同,批量 API 可让您在一次调用中创建、更新和删除许多文档。但是,您通常在请求正文中指定这些操作,而不是在请求 URL 中。由于 OpenSearch Service 使用 URL 控制对域子资源的访问,事实上,test-user 可以使用批量 API 对 restricted-index 进行更改。即使该用户缺乏对索引的 POST 权限,以下请求也将成功

POST https://search-test-domain.us-west-1.es.amazonaws.com/_bulk { "index" : { "_index": "restricted-index", "_type" : "movie", "_id" : "1" } } { "title": "Your Name", "director": "Makoto Shinkai", "year": "2016" }

在这种情况下,访问策略无法实现其意图。要防止用户绕过这些类型的限制,您可以将 rest.action.multi.allow_explicit_index 更改为 false。如果此值为 false,则对批量、mget 和 msearch API 的所有在请求正文中指定索引名称的调用都将停止工作。换句话说,对 _bulk 的调用不再有效,但对 test-index/_bulk 的调用仍然有效。这第二个终端节点包含一个索引名称,因此您无需在请求正文中指定一个索引名称。

OpenSearch 控制面板高度依赖于 mget 和 msearch,因此它不太可能在此更改后正常工作。若要进行部分补救,您可以将 rest.action.multi.allow_explicit_index 保留为 true 或拒绝特定用户访问这些 API 中的一个或多个。

有关更改此设置的信息,请参阅高级集群设置

同样,以下基于资源的策略包含两个小问题:

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": "arn:aws:iam::123456789012:user/test-user" }, "Action": "es:ESHttp*", "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/*" }, { "Effect": "Deny", "Principal": { "AWS": "arn:aws:iam::123456789012:user/test-user" }, "Action": "es:ESHttp*", "Resource": "arn:aws:es:us-west-1:987654321098:domain/test-domain/restricted-index/*" } ] }
  • 即使显式拒绝,test-user 仍然可以进行 GET https://search-test-domain.us-west-1.es.amazonaws.com/_all/_searchGET https://search-test-domain.us-west-1.es.amazonaws.com/*/_search 等调用,以访问 restricted-index 中的文档。

  • 由于 Resource 元素引用 restricted-index/*test-user 无权直接访问索引的文档。但是,该用户有权删除整个索引。要防止访问和删除,策略必须改为指定 restricted-index*

与混合广泛的允许和集中的拒绝相比,最安全的方法是遵循最小特权原则,仅授予执行任务所需的权限。有关控制对各个索引或 OpenSearch 操作的访问的更多信息,请参阅 在 Amazon OpenSearch Service 中进行精细访问控制

重要

指定 * 通配符将启用对域的匿名访问。不建议使用通配符。此外,还要仔细检查以下策略,以确认不会授予广泛的访问权限:

  • 附加到关联 AWS 主体(例如 IAM 角色)的基于身份的策略

  • 附加到关联 AWS 资源(例如 AWS Key Management Service KMS 密钥)的基于资源的策略

配置访问策略

  • 有关在 OpenSearch Service 中创建或修改基于资源和基于 IP 的策略的说明,请参阅 配置访问策略

  • 有关在 IAM 中创建或修改基于身份的策略的说明,请参阅《IAM 用户指南》中的创建 IAM policy

其他示例策略

虽然本章包含许多示例策略,但 AWS 访问控制是一个复杂的主题,最好是通过示例理解。有关更多信息,请参阅 IAM 用户指南IAM 基于身份的策略示例