建立具有多個索引鍵或值的條件 - AWS Identity and Access Management

建立具有多個索引鍵或值的條件

您可以使用政策的 Condition 元素來測試請求中單一金鑰的多個金鑰或多個值。當您對 AWS 提出請求時,不論是透過程式設計方式或透過 AWS Management Console,您的請求會包含委託人、操作、標籤等的相關資訊。若要了解請求中包含的資訊和資料,請參閱 要求。您可以使用條件索引鍵來測試請求中相符索引鍵的值。例如,您可以使用條件索引鍵來控制 DynamoDB 資料表的特定屬性存取,或根據索引標籤來控制 Amazon EC2 執行個體的特定屬性存取。

Condition 元素可以包含多個條件,而且每個條件可以包含多個索引鍵值對。大多數條件金鑰都支援使用多個值。下圖說明了這一點。除非另有說明,否則,所有索引鍵都可以擁有多個值。

具有多個索引鍵或值的條件評估邏輯

如果您的政策有多個條件運算子或連接到單一條件運算子的多個金鑰,則使用邏輯 AND 評估這些條件。如果單一條件運算子包含一個索引鍵的多個值,則使用邏輯 OR 評估該條件運算子。所有條件必須解析為 True,才能觸發所需要的 AllowDeny 效果。


            條件區塊顯示如何將 AND 和 OR 套用到多個值
注意

在政策中為否定相符條件運算子 (例如 StringNotEqualsDateNotEquals) 列出多個值時,有效許可的運作類似於邏輯 AND。例如,如果在 StringNotEquals 條件運算子中有多個 aws:PrincipalAccount 值,則字串不能符合任何列出的 aws:PrincipalAccount 值以將條件解析為 true。

使用多個金鑰和值

若要將您的條件與具有多個鍵值的請求內容進行比較,您必須使用 ForAllValuesForAnyValue 設定運算子。這些集合運算子用於比較兩組值。

當政策條件比較兩個集合的值 (例如請求中的標籤集和政策條件中的標籤集) 時,您需要告訴 AWS 如何比較集合。IAM 定義了兩個集合運算子,ForAnyValueForAllValues。必須將集合運算子與多值條件金鑰搭配使用。請勿將集合運算子與單一值條件索引鍵搭配使用。

若要判斷 AWS 條件金鑰是否是單值或多值,請查看其資料類型。若要檢視服務的條件金鑰資料類型,請參閱AWS 服務的動作、資源和條件金鑰並選擇您想要檢視其條件金鑰的服務。如果條件 Type (類型) 欄位包括 ArrayOf 字首,則條件金鑰為多值。例如:AWS Key Management Service 支援 String 單值資料類型和 ArrayOfString 多值資料類型的條件金鑰。

  • 單值條件金鑰在請求內容中最多有一個值。例如,您可以在 AWS 中標記資源。資源標籤儲存為標籤金鑰/值對。資源標籤鍵可以有單一標籤值。因此,aws:ResourceTag/tag-key 是單值條件金鑰。請勿使用具有單一值條件索引鍵的集合運算子。

  • 多值條件金鑰在請求內容中可以擁有多個值。例如,您在 AWS 中標記資源並在請求中包含多個標籤金鑰/值對。因此,aws:TagKeys 是多值條件金鑰。多值條件金鑰需要集合運算子。

ForAllValuesForAnyValue 限定詞新增設定操作功能到條件運算子,以便您可以針對多個條件值測試多個請求值。此外,如果您在政策中使用萬用字元或變數包含多重值字串金鑰,您也必須使用 StringLike 條件運算子。對於包含單一金鑰之多個值的請求,您必須像陣列一樣在括號內括住條件金鑰值。例如,"Key2":["Value2A", "Value2B"]

  • ForAllValues — 與多值條件金鑰搭配使用。測試請求集每個成員的值是否為條件金鑰集的子集。如果請求中每個索引鍵值至少符合政策中的一個值,則條件會傳回 true。如果請求中沒有索引鍵,或索引鍵值解析為 null 資料集 (例如空白字串),則也會傳回 true。請勿將 ForAllValuesAllow 效果搭配使用,因為可能會過於寬容。

  • ForAnyValue — 與多值條件金鑰搭配使用。測試這組請求值是否至少有一個成員符合這組條件索引鍵值的至少一個成員。如果請求中任一鍵值符合政策中的任一條件值,則條件會傳回 true。如果沒有相符金鑰或為 null 資料集,則條件會傳回 false。

    注意

    單值和多值條件金鑰之間的差異取決於請求內容中值的數目,而非政策條件中值的數目。

使用多個值搭配條件設定運算子的範例

您可以建立政策,針對您在政策中指定的一或多個值測試請求中的多個值。假設您有名為 Thread 的 Amazon DynamoDB 資料表,用於存放技術支援論壇中貼文的資訊。資料表具有名為 IDUserNamePostDateTimeMessageTags 的屬性。

{ ID=101 UserName=Bob PostDateTime=20130930T231548Z Message="A good resource for this question is docs.aws.amazon.com" Tags=["AWS", "Database", "Security"] }

如需有關設定運算子如何用於 DynamoDB 以實作精細設定個別資料項目和屬性的存取權的詳細資訊,請參閱 Amazon DynamoDB 開發人員指南中的 DynamoDB 的精細存取控制

您可以建立政策,只允許使用者查看 PostDateTimeMessageTags 屬性。如果使用者的請求包含任何這些屬性,則允許此請求。但是,如果請求包含任何其他屬性 (例如,ID),請求會被拒絕。從邏輯上來說,您想要建立允許屬性的清單 (PostDateTimeMessageTags)。您想要在政策中指出,所有使用者請求的屬性必須在允許的屬性清單中。

以下範例政策說明如何使用 ForAllValues 限定詞與 StringEquals 條件運算子。條件「只」允許使用者請求名為 Thread 之 DynamoDB 資料表中的 IDMessageTags 屬性。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": "dynamodb:GetItem", "Resource": "arn:aws:dynamodb:*:*:table/Thread", "Condition": { "ForAllValues:StringEquals": { "dynamodb:Attributes": [ "ID", "Message", "Tags" ] } } } ] }

假設使用者向 DynamoDB 發出請求來從 Thread 資料表取得屬性 MessageTags。在這種情況下,會允許此請求,因為使用者請求的屬性都符合政策中指定的值。GetItem 操作要求使用者傳遞 ID 屬性做為資料庫資料表索引鍵,這在政策中也是被允許的。不過,如果使用者的請求包含 UserName 屬性,則請求會失敗。原因是 UserName 不在允許的屬性清單中,且 ForAllValues 限定詞會要求要列在政策中的所有請求值。

重要

如果使用 dynamodb:Attributes,您必須指定資料表的所有主金鑰和金鑰屬性的名稱。您還必須指定政策中所列的任何次要索引。否則,DynamoDB 無法使用這些金鑰屬性來執行所請求的動作。

或者,您可能會想要確保明確禁止使用者在請求中包含一些屬性,例如 IDUserName 屬性。例如,當使用者更新 DynamoDB 資料表時,您可能會排除屬性,因為更新 (PUT 操作) 不應變更特定屬性。在這種情況下,您會建立禁止屬性的清單 (IDUserName)。如果任何使用者請求的屬性符合任何禁止的屬性,則請求會遭拒。

以下範例顯示,如果使用者嘗試執行的 ForAnyValue 動作,如何使用 ID 限定詞拒絕存取 PostDateTimePutItem 屬性。也就是說,如果使用者嘗試更新 Thread 表格中的其中一個屬性。請注意,Effect 元素已設為 Deny

{ "Version": "2012-10-17", "Statement": { "Effect": "Deny", "Action": "dynamodb:PutItem", "Resource": "arn:aws:dynamodb:*:*:table/Thread", "Condition": { "ForAnyValue:StringEquals": { "dynamodb:Attributes": [ "ID", "PostDateTime" ] } } } }

假設使用者發出更新 PostDateTime 表格的 MessageThread 屬性的請求。ForAnyValue 限定詞會判斷任何請求的屬性是否出現在政策的清單中。在這種情況下,有一項符合 (PostDateTime),所以條件為 true。假設請求中的其他值 (例如,資源),也符合整體政策,評估會傳回 true。因為政策的效用是 Deny,所以請求被拒絕。

試想使用者改為發出執行只具有 PutItem 屬性的 UserName 的請求。請求中的無任何屬性 (只有 UserName) 符合政策中所列的任何屬性 (IDPostDateTime)。條件會傳回 false,因此政策的效用 (Deny) 也會是 false,而請求不會被此政策拒絕。(若要讓請求成功,必須由不同政策明確允許。而其未被此政策明確拒絕,但隱含地拒絕所有請求)。

警告

當您使用 ForAllValues 條件運算子時,如果請求中沒有索引鍵,或索引鍵值解析為 null 資料集 (例如空白字串),則會傳回 true。若要要求請求包含至少一個值,您必須在政策中使用另一個條件。如需範例,請參閱 在 AWS 請求期間控制存取許可

多個值搭配條件設定運算子的評估邏輯

本節討論使用 ForAllValuesForAnyValue 運算子之評估邏輯的規格。下表說明可能會包含在請求中的可能金鑰 (PostDateTimeUserName) 以及包含值 PostDateTimeMessageTags 的政策條件。

金鑰 (請求中)

條件值 (政策中)

PostDateTime

PostDateTime

UserName

Message

 

Tags

組合的評估如下所示:

PostDateTime 與 相符?PostDateTime

PostDateTime 與 相符?Message

PostDateTime 與 相符?Tags

UserName 與 相符?PostDateTime

UserName 與 相符?Message

UserName 與 相符?Tags

條件運算子的結果取決於使用哪些修飾詞搭配政策條件:

  • ForAllValues. 如果請求中的每個索引鍵 (PostDateTimeUserName) 與政策中至少一個條件值 (PostDateTimeMessageTags) 相符,條件運算子會傳回 true。以另一種方式表示,為了讓條件為 true,(PostDateTime 必須等於 PostDateTimeMessageTags)「並且」(UserName 必須等於 PostDateTimeMessageTags)。

  • ForAnyValue. 如果請求值和政策值的任意組合 (範例中六個的任何其中一個) 傳回 true,則條件運算子會傳回 true。

以下政策包括 ForAllValues 限定詞:

{ "Version": "2012-10-17", "Statement": { "Effect": "Allow", "Action": "dynamodb:GetItem", "Resource": "arn:aws:dynamodb:*:*:table/Thread", "Condition": { "ForAllValues:StringEquals": { "dynamodb:Attributes": [ "PostDateTime", "Message", "Tags" ] } } } }

假設使用者對 DynamoDB 提出請求,以取得 PostDateTimeUserName 屬性。組合的評估如下所示:

PostDateTime 與 相符?PostDateTime

True

PostDateTime 與 相符?Message

False

PostDateTime 與 相符?Tags

False

UserName 與 相符?PostDateTime

False

UserName 與 相符?Message

False

UserName 與 相符?Tags

False

政策包含 ForAllValues 條件運算子修飾詞,表示 PostDateTime 必須至少有一個相符,以及 UserName 有一個相符。UserName 沒有相符者,因此條件運算子傳回 false,而政策不允許該請求。

以下政策包括 ForAnyValue 限定詞:

{ "Version": "2012-10-17", "Statement": { "Effect": "Deny", "Action": "dynamodb:PutItem", "Resource": "arn:aws:dynamodb:*:*:table/Thread", "Condition": { "ForAnyValue:StringEquals": { "dynamodb:Attributes": [ "ID", "PostDateTime" ] } } } }

請注意,政策包括 "Effect":"Deny" 且動做為 PutItem。假設使用者發出 PutItem 請求,其包括屬性 UserNameMessagePostDateTime。評估如下所示:

UserName 與 相符?ID

False

UserName 與 相符?PostDateTime

False

Messages 與 相符?ID

False

Message 與 相符?PostDateTime

False

PostDateTime 與 相符?ID

False

PostDateTime 與 相符?PostDateTime

True

透過修飾詞 ForAnyValue,如果這些測試中的任何一個傳回 true,條件就會傳回 true。上次測試傳回 true,所以條件為 true,因為 Effect 元素設為 Deny,而請求被拒絕。

注意

如果請求中的鍵值解析為空的資料集 (如空白清單),以 ForAllValues 修改的條件運算子會傳回 true。由 ForAnyValue 修改的條件運算子會傳回 false。