策略评估逻辑 - AWS Identity and Access Management

策略评估逻辑

在主体尝试使用 AWS Management Console、AWS API 或 AWS CLI 时,该主体将向 AWS 发送请求。在 AWS 服务收到请求时,AWS 会完成几个步骤来确定是允许还是拒绝该请求。

  1. 身份验证 - AWS 首先对发出请求的主体进行身份验证(如有必要)。有一些服务(如 Amazon S3)不需要此步骤,它们允许来自匿名用户的某些请求。

  2. 处理请求上下文 - AWS 处理在请求中收集的信息以确定应用于请求的策略。

  3. 评估单个账户中的策略 - AWS 评估所有策略类型,这会影响策略的评估顺序。

  4. 确定是允许还是拒绝账户内的请求 – AWS 然后根据请求上下文处理策略以确定是允许还是拒绝请求。

处理请求上下文

AWS 处理请求以将以下信息收集到请求上下文 中:

  • Actions (or operations)(操作(或运营))- 主体希望执行的操作。

  • Resources(资源)- 对其执行操作的 AWS 资源对象。

  • Principal(主体)- 发送请求的用户、角色、联合身份用户或应用程序。有关主体的信息包括与该主体关联的策略。

  • 环境数据 – 有关 IP 地址、用户代理、SSL 启用状态或当天时间的信息。

  • 资源数据 – 与请求的资源相关的数据。这可能包括 DynamoDB 表名称或 Amazon EC2 实例上的标签等信息。

AWS 随后使用此类信息来查找应用于请求上下文的策略。

评估单个账户中的策略

AWS 如何评估策略取决于适用于请求上下文的策略类型。可在单个 AWS 账户中使用以下策略类型,它们按使用频率顺序列出。有关这些策略类型的更多信息,请参阅IAM 中的策略和权限。。要了解 AWS 如何评估跨账户访问策略,请参阅跨账户策略评估逻辑

  1. 基于身份的策略 — 基于身份的策略附加到 IAM 身份(用户、用户组或角色)并向 IAM 实体(用户和角色)授予权限。如果仅基于身份的策略适用于请求,则 AWS 检查所有这些策略以找到至少一个 Allow

  2. Resource-based policies(基于资源的策略)- 基于资源的策略将权限授予指定为主体的主体(账户、用户、角色和会话主体,如角色会话和 IAM 联邦用户)。权限定义主体可以对策略附加到的资源执行哪些操作。如果基于资源的策略和基于身份的策略同时适用于请求,则 AWS 检查所有这些策略以找到至少一个 Allow 。评估基于资源的策略时,策略中指定的主体 ARN 决定了其他策略类型中的隐式拒绝是否适用于最终决策。

  3. IAM 权限边界 - 权限边界是一项高级功能,借助该功能,您可以设置基于身份的策略可以授予 IAM 实体(用户或角色)的最大权限。当您设置实体的权限边界时,该实体只能执行其基于身份的策略和其权限边界同时允许的操作。某些情况下,权限边界中的隐式拒绝可能会限制由基于资源的策略所授予的权限。要了解更多信息,请稍后参阅本主题中的 确定是允许还是拒绝账户内的请求

  4. AWS Organizations 服务控制策略 (SCP) - Organizations SCP 指定企业或企业单元 (OU) 的最大权限。SCP 最大权限适用于成员账户中主体的权限,包括每个 AWS 账户 根用户。如果 SCP 存在,仅当基于身份的策略和基于资源的策略以及 SCP 允许该操作时,才向成员账户中的主体授予这些权限。如果权限边界和 SCP 同时存在,则边界、SCP 以及基于身份的策略必须全部允许操作。

  5. Session policies(会话策略)- 会话策略是高级策略,在以编程方式为角色或联合身份用户创建临时会话时,这些策略将作为参数进行传递。要以编程方式创建角色会话,请使用 AssumeRole* API 操作之一。在执行该操作并传递会话策略时,生成的会话的权限是 IAM 实体的基于身份的策略与会话策略的交集。要创建联合身份用户会话,您需要使用 IAM 用户的访问密钥以编程方式调用 GetFederationToken API 操作。基于资源的策略对会话策略权限评估具有不同的影响。这种差异取决于用户或角色的 ARN 还是会话的 ARN 在基于资源的策略中作为主体列出。有关更多信息,请参阅会话策略

请记住,任一项策略中的显式拒绝将覆盖允许。

评估基于身份的策略以及基于资源的策略

基于身份的策略和基于资源的策略向策略所附加到的身份或资源授予权限。在 IAM 实体(用户或角色)请求访问同一账户中的资源时,AWS 评估基于身份的策略和基于资源的策略授予的所有权限。生成的权限是指两种类型的权限的总和。如果基于身份的策略和/或基于资源的策略允许此操作,则 AWS 允许执行该操作。其中任一项策略中的显式拒绝将覆盖允许。


          评估基于身份的策略和基于资源的策略

评估具有权限边界的基于身份的策略

在 AWS 评估用户的基于身份的策略和权限边界时,生成的权限是这两种类别的交集。这意味着,当您通过现有基于身份的策略向用户添加权限边界时,您可能会减少用户可以执行的操作。或者,当您从用户删除权限边界时,您可能会增加用户可以执行的操作。其中任一项策略中的显式拒绝将覆盖允许。要查看有关如何使用权限边界评估其他策略类型的信息,请参阅评估具有边界的有效权限


          评估基于身份的策略和权限边界

评估具有 Organizations SCP 的基于身份的策略

在用户属于作为组织成员的账户时,生成的权限是用户的策略与 SCP 的交集。这意味着,操作必须由基于身份的策略和 SCP 同时允许。其中任一项策略中的显式拒绝将覆盖允许。


          评估基于身份的策略和 SCP

您可以在 AWS Organizations 中了解您的账户是否为某个组织的成员。组织成员可能会受 SCP 的影响。要使用 AWS CLI 命令或 AWS API 操作查看该数据,您必须具有 Organizations 实体的 organizations:DescribeOrganization 操作的权限。您必须具有额外的权限才能在 Organizations 控制台中执行该操作。要了解 SCP 是否拒绝访问特定的请求或更改您的有效权限,请与您的 AWS Organizations 管理员联系。

确定是允许还是拒绝账户内的请求

假设主体向 AWS 发送请求以访问与主体的实体相同的账户中的资源。AWS 执行代码决定是应该允许还是拒绝请求。AWS 评估适用于请求上下文的所有策略。下面概括介绍了单个账户中有关这些策略的 AWS 评估逻辑。

  • 默认情况下,除 AWS 账户 根用户外,所有请求都被隐式否定,具有完全访问权限。

  • 基于身份或基于资源的策略中的显式允许将覆盖此默认值。

  • 如果存在权限边界、Organizations SCP 或会话策略,它可能会使用隐式拒绝覆盖允许。

  • 任何策略中的显式拒绝将覆盖任何允许。

以下流程图提供了如何做出决定的详细信息。此流程图不涵盖基于资源的策略和其他类型策略中隐含拒绝的影响。


        评估流程图
  1. Deny evaluation(拒绝评估)- 默认情况下,所有请求都被拒绝。这称为隐式拒绝。AWS 执行代码评估账户中应用于请求的所有策略。其中包含 AWS Organizations SCP、基于资源的策略、基于身份的策略、IAM 权限边界和会话策略。在所有这些策略中,执行代码查找应用于请求的 Deny 语句。这称为显式拒绝。如果代码找到一个适用的显式拒绝,则代码将返回最终决定拒绝。如果没有显式拒绝,则代码会继续。

  2. Organizations SCP - 然后,代码评估适用于请求的 AWS Organizations 服务控制策略 (SCP)。SCP 适用于附加 SCP 的账户的主体。如果执行代码没有在 SCP 中找到任何适用的 Allow 语句,则隐式拒绝请求。代码将返回拒绝最终决定。如果没有 SCP,或者 SCP 允许所请求的操作,则代码继续。

  3. 基于资源的策略 — 在同一账户中,基于资源的策略会对策略评估产生不同的影响,具体取决于访问资源的主体类型以及基于资源的策略中允许的主体。根据主体的类型,Allow 在基于资源的策略中可能会导致最终决定 Allow,即使基于身份的策略、权限边界或会话策略中存在隐式拒绝。

    对于大多数资源,您只需要在基于身份的策略或基于资源的策略中明确授予主体访问权限。IAM 角色信任策略KMS 密钥策略是此逻辑的例外,因为它们必须明确允许主体的访问权限。

    当指定的主体是 IAM 用户、IAM 角色或会话主体时,基于资源的策略逻辑会与其他策略类型有所不同。会话主体包括 IAM 角色会话或者 IAM 联合身份用户会话。如果基于资源的策略直接向提出请求的 IAM 用户或会话主体授予权限,则基于身份的策略、权限边界或会话策略中的隐式拒绝不会影响最终决策。

    如果基于身份的策略、权限边界和会话策略中存在隐式拒绝,则下表有助于您了解基于资源的策略对不同主体类型的影响。

    基于资源的策略和其他策略类型的隐式拒绝(同一账户)
    提出请求的主体 基于资源的策略 基于身份的策略 权限边界 会话策略 结果 Reason
    IAM 角色 不适用 不适用 不适用 不适用 不适用 角色本身无法提出请求。在担任角色之后,向角色会话发出请求。
    IAM 角色会话 允许角色 ARN 隐式拒绝 隐式拒绝 隐式拒绝 DENY 权限边界和会话策略将作为最终决策的一部分进行评估。任何一项策略中的隐式拒绝都会导致拒绝决定。
    IAM 角色会话 允许角色会话 ARN 隐式拒绝 隐式拒绝 隐式拒绝 允许 权限直接授予会话。其他策略类型不影响决策。
    IAM 用户 允许 IAM 用户 ARN 隐式拒绝 隐式拒绝 不适用 允许 权限直接授予会话。其他策略类型不影响决策。
    IAM 联合身份用户 (GetFederationToken) 允许 IAM 用户 ARN 隐式拒绝 隐式拒绝 隐式拒绝 DENY 权限边界或会话策略中的隐式拒绝将导致 DENY。
    IAM 联合身份用户 (GetFederationToken) 允许 IAM 联合身份用户会话 ARN 隐式拒绝 隐式拒绝 隐式拒绝 允许 权限直接授予会话。其他策略类型不影响决策。
    根用户 允许根用户 ARN 不适用 不适用 不适用 允许 根账户可以不受限制地访问 AWS 账户中的所有资源。要了解如何在 AWS Organizations 中控制对账户的根用户的访问权限,请参阅 Organizations 用户指南中的服务控制策略 (SCP)
    AWS 服务主体 允许 AWS 服务主体 不适用 不适用 不适用 允许 当基于资源的策略直接向 AWS 服务主体,其他策略类型不会影响决策。
    • IAM 角色— 授予 IAM 角色 ARN 权限的基于资源的策略受权限边界或会话策略中隐式拒绝的限制。

      角色示例 ARN

      arn:aws:iam::111122223333:role/examplerole
    • IAM 角色会话— 在同一账户中,向 IAM 角色会话 ARN 授予权限的基于资源的策略直接向担任的角色会话授予权限。直接授予会话的权限不受基于身份的策略、权限边界或会话策略中的隐式拒绝的限制。当您担任角色并提出请求时,发出请求的主体是 IAM 角色会话 ARN,而不是角色本身的 ARN。

      示例角色会话 ARN

      arn:aws:sts::111122223333:assumed-role/examplerole/examplerolesessionname
    • IAM 用户 – 在同一账户中,向 IAM 用户 ARN(不是联合身份用户会话)授予权限的基于资源的策略不受基于身份的策略或权限边界中隐式拒绝的限制。

      示例 IAM 用户 ARN

      arn:aws:iam::111122223333:user/exampleuser
    • IAM 联合身份用户会话— IAM 联合身份用户会话是通过调用 GetFederationToken 创建的会话。当联合身份用户发出请求时,发出请求的主体是联合身份用户 ARN,而不是联合身份的 IAM 用户的 ARN。在同一个账户中,将权限授予联合身份用户 ARN 的基于资源的策略直接将权限授予会话。直接授予会话的权限不受基于身份的策略、权限边界或会话策略中的隐式拒绝的限制。

      但是,如果基于资源的策略向联合身份的 IAM 用户的 ARN 授予权限,则联合身份用户在会话期间发出的请求将受权限边界或会话策略中隐式拒绝的限制。

      示例 IAM 联合身份用户会话 ARN

      arn:aws:sts::111122223333:federated-user/exampleuser
  4. Identity-based policies(基于身份的策略)- 代码随后会检查主体的基于身份的策略。对于 IAM 用户,这包括用户策略和来自用户所属组的策略。如果没有基于身份的策略或者基于身份的策略中没有允许请求动作的语句,那么请求被隐式否定,代码返回 Deny 的一个最终决定。如果任何适用的基于身份的策略中的任何语句都允许请求的动作,则代码继续适用。

  5. IAM 权限边界 - 代码随后会检查主体使用的 IAM 实体是否具有权限边界。如果用于设置权限边界的策略不允许所请求的操作,则请求会被隐式拒绝。代码将返回拒绝最终决定。如果没有权限边界,或者权限边界允许所请求的操作,则代码继续。

  6. 会话策略 – 然后代码检查主体是否为会话主体。会话主体包括 IAM 角色会话或者 IAM 联合身份用户会话。如果主体不是会话主体,执行代码将返回 Allow 的最终决定。

    对于会话负责人,他的代码检查请求中是否传递了会话策略。您可以传递会话策略,同时使用 AWS CLI 或 AWS API 为某个角色或 IAM 联合身份用户获取临时凭证。

    • 如果会话策略存在但不允许所请求的操作,则请求会被隐式拒绝。代码将返回拒绝最终决定。

    • 如果没有会话策略,则代码将检查主体是否为角色会话。如果主体是角色会话,那么请求是已允许。否则,请求被隐式拒绝,代码返回 Deny 的最终判决。

    • 如果会话策略在场并允许请求的动作,那么执行代码返回一个 Allow 的最终决策。

  7. Errors(错误)- 如果 AWS 执行代码在评估过程中的任意点遇到错误,它将生成异常并关闭。

基于身份的策略和基于资源的策略评估示例

策略的最常见类型是基于身份的策略和基于资源的策略。

假定 Carlos 具有用户名 carlossalazar,他尝试将文件保存到 carlossalazar-logs Amazon S3 存储桶。

还假定将以下策略附加到 carlossalazar IAM 用户。

{ "Version": "2012-10-17", "Statement": [ { "Sid": "AllowS3ListRead", "Effect": "Allow", "Action": [ "s3:GetBucketLocation", "s3:GetAccountPublicAccessBlock", "s3:ListAccessPoints", "s3:ListAllMyBuckets" ], "Resource": "arn:aws:s3:::*" }, { "Sid": "AllowS3Self", "Effect": "Allow", "Action": "s3:*", "Resource": [ "arn:aws:s3:::carlossalazar/*", "arn:aws:s3:::carlossalazar" ] }, { "Sid": "DenyS3Logs", "Effect": "Deny", "Action": "s3:*", "Resource": "arn:aws:s3:::*log*" } ] }

此策略中的 AllowS3ListRead 语句允许 Carlos 查看账户中的所有存储桶的列表。AllowS3Self 语句允许 Carlos 完全访问与其用户名同名的存储桶。DenyS3Logs 语句拒绝 Carlos 访问名称中包含 log 的任何 S3 存储桶。

此外,以下基于资源的策略(称为存储桶策略)附加到 carlossalazar 存储桶。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": "arn:aws:iam::123456789012:user/carlossalazar" }, "Action": "s3:*", "Resource": [ "arn:aws:s3:::carlossalazar/*", "arn:aws:s3:::carlossalazar" ] } ] }

此策略指定只有 carlossalazar 用户可以访问 carlossalazar 存储桶。

当 Carlos 请求将文件保存到 carlossalazar-logs 存储桶时,AWS 将确定应用于请求的策略。在此示例中,仅基于身份的策略和基于资源的策略适用。这些都是权限策略。由于没有任何权限边界适用,评估逻辑将减少为以下逻辑。


        评估流程图

AWS 首先检查应用于请求上下文的 Deny 语句。它找到一个,因为基于身份的策略显式拒绝 Carlos 访问用于日志记录的任何 S3 存储桶。拒绝 Carlos 访问。

假设他随后意识到自己的错误,尝试将文件保存到 carlossalazar 存储桶。AWS 检查 Deny 语句,但未找到。然后,它检查权限策略。基于身份的策略和基于资源的策略均允许请求。因此,AWS 允许请求。如果其中任何一个显式拒绝了语句,则将拒绝请求。如果其中一种策略类型允许请求,而另一种不允许,则仍允许请求。

显式拒绝和隐式拒绝之间的区别

如果适用策略包含 Deny 语句,则请求会导致显式拒绝。如果应用于请求的策略包含一个 Allow 语句和一个 Deny 语句,Deny 语句优先于 Allow 语句。将显式拒绝请求。

当没有适用的 Deny 语句但也没有适用的 Allow 语句时,会发生隐式拒绝。由于原定设置下拒绝访问 IAM 主体,因此必须显式允许他们执行操作。否则,将隐式拒绝他们访问。

在设计授权战略时,您必须创建包含 Allow 语句的策略才能允许主体成功发出请求。但是,您可以选择显式拒绝和隐式拒绝的任意组合。

例如,您可以创建以下策略,其中包括允许的操作、隐式拒绝的操作和显式拒绝的操作。AllowGetList 语句允许对 IAM 操作的只读权限,这些操作以 GetList 为前缀。IAM 中的所有其他操作,例如 iam:CreatePolicy隐式拒绝DenyReports 语句通过拒绝对包含 Report 后缀(例如 iam:GetOrganizationsAccessReport)的操作的访问权限,显式拒绝对 IAM 报告的访问权限。如果有人向此主体添加另一个策略以授予他们访问 IAM 报告的权限(例如 iam:GenerateCredentialReport),由于这种明确拒绝,报告相关请求仍被拒绝。

{ "Version": "2012-10-17", "Statement": [ { "Sid": "AllowGetList", "Effect": "Allow", "Action": [ "iam:Get*", "iam:List*" ], "Resource": "*" }, { "Sid": "DenyReports", "Effect": "Deny", "Action": "iam:*Report", "Resource": "*" } ] }