首页 文章

如何将S3存储桶策略写入* *仅允许特定的IAM角色和Cloudfront Origin Access Identity?

提问于
浏览
2

我的总体目标:我尝试了几件事并阅读了相关的AWS文档,但我无法确定如何编写S3存储桶策略以仅允许访问特定的IAM角色和Cloudfront Origin Access Identity(OAI),并拒绝其他所有人 .

到目前为止我尝试过的内容:1 . 我发现了这个博客,其中展示了如何限制对特定IAM角色的s3桶访问:https://aws.amazon.com/blogs/security/how-to-restrict-amazon-s3-bucket-access-to-a-specific-iam-role/ 2.基于上述博客,我编写了以下存储桶策略 . 此策略仅允许MY_IAM_ROLE允许对名为'myBucket'的存储桶执行所有操作:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Deny",
            "Principal": "*",
            "Action": "s3:*",
            "Resource": [
                "arn:aws:s3:::myBucket",
                "arn:aws:s3:::myBucket/*"
            ],
            "Condition": {
                "StringNotLike": {
                    "aws:userId": [
                        "MY_IAM_ROLE_USER_ID:*"
                    ]
                }
            }
        }
    ]
}

我的问题: How can I combine (1) aws:userid of IAM roles/users and (2) OAI IDs in a single policy statement?

4 回答

  • 0

    这似乎有点远,但找到Origin Access Identity的ID(不是规范的用户ID ...找到以 E 开头并且大约12个字符长的那个)并将其添加到策略中,如下所示:

    "StringNotLike": {
       "aws:userId": [
          "MY_IAM_ROLE_USER_ID:*",
          "arn:aws:iam::cloudfront:user/CloudFront Origin Access Identity EXXEXAMPLEXX"
       ]
     }
    

    请注意,包含空格的单词“CloudFront Origin Access Identity”是此引用字符串的一部分 . 完全如图所示插入,仅更改12个字符ID .

    这可能会阻止此政策拒绝访问OAI . 如果有办法将OAI的用户包含在条件键中,这似乎是唯一可行的解决方案 .

    另外,您需要第二个策略声明,即允许对OAI进行必要访问的正常声明 .

  • 0

    回顾一下,您需要一个限制访问S3存储桶和内容的存储桶策略,但允许访问您希望指定的Cloudfront Origin Access Identity以及您的IAM角色 . 我有几种方法可以做到这一点,一个使用NotPrincipal元素,另一个使用Principal元素 . 这取决于有多少人使用您的IAM角色,或者您是否计划扩展对角色的访问权限 . 您可以通过使用NotPrincipal元素和显式拒绝在存储桶策略中指定权限来阻止Amazon Identify和Access Management(IAM)实体访问您的Amazon S3存储桶 . 但是,NotPrincipal不支持通配符 .

    在此策略示例中,您必须列出每个用户的角色会话名称以及将承担该角色的每个实例ID:

    "Effect": "Deny",
    "NotPrincipal": {
    "AWS": [
        "arn:aws:sts::444455556666:assumed-role/cross-account-read-only-role/cross-account-audit-app",
        "arn:aws:sts::444455556666:assumed-role/cross-account-read-only-role/instanceID",
        "arn:aws:iam::444455556666:role/cross-account-read-only-role",
        "arn:aws:iam::444455556666:root"
        ]
    }
    

    要覆盖所有这些用户和实例,您需要在语句中使用通配符来表示假定的角色:

    "arn:aws:sts::444455556666:assumed-role/cross-account-read-only-role/*"
    

    However, wildcards are not supported with the NotPrincipal element. 如果您只使用角色或一个实例,这将起作用,但在扩展时,您需要为假定角色的用户/实例添加ARN .

    在此示例中,使用 "Principal": "*" 作为每个语句块中的目标实体,而不是 NotPrincipal ,其中包括每个允许块的条件 . "aws:userid": ["ROLE-ID:*"] 中使用通配符来包括调用进程(例如应用程序,服务或实例ID)在调用获取临时凭据时传递的所有名称 . 有关更多信息,请参阅所有请求中可用的信息 . 包含root帐户以防止锁定:

    "Condition": {
        "StringLike": {
            "aws:userid": [
                "AROAID2GEXAMPLEROLEID:*",
                "444455556666"
            ]
        }
    }
    

    拒绝块中的StringNotLike:

    "Condition": {
        "StringNotLike": {
            "aws:userid": [
                "AROAID2GEXAMPLEROLEID:*",
                "444455556666"
            ]
        }
    }
    

    这是完整的政策:

    {
        "Version": "2012-10-17",
        "Statement": [
            {
                "Sid": "",
                "Effect": "Allow",
                "Principal": "*",
                "Action": [
                    "s3:ListBucket"
                ],
                "Resource": "arn:aws:s3:::myExampleBucket",
                "Condition": {
                    "StringLike": {
                        "aws:userid": [
                            "AROAID2GEXAMPLEROLEID:*",
                            "444455556666"
                        ]
                    }
                }
            },
            {
                "Sid": "",
                "Effect": "Allow",
                "Principal": "*",
                "Action": [
                    "s3:DeleteObject",
                    "s3:GetObject",
                    "s3:PutObject"
                ],
                "Resource": "arn:aws:s3:::myExampleBucket/*",
                "Condition": {
                    "StringLike": {
                        "aws:userid": [
                            "AROAID2GEXAMPLEROLEID:*",
                            "444455556666"
                        ]
                    }
                }
            },
            {
                "Sid": "",
                "Effect": "Deny",
                "Principal": "*",
                    "Action": "s3:*",
                    "Resource": [
                        "arn:aws:s3:::myExampleBucket/*",
                        "arn:aws:s3:::myExampleBucket"
                    ],
                    "Condition": {
                        "StringNotLike": {
                            "aws:userid": [
                                "AROAID2GEXAMPLEROLEID:*",
                                "444455556666"
                            ]
                        }
                    }
                }
            ]
    }
    

    注意:请确保使用您自己的角色ID和存储桶名称替换示例名称 . 在上面的示例中,我使用了IAM实体的唯一ID . http://docs.aws.amazon.com/IAM/latest/UserGuide/reference_identifiers.html#identifiers-unique-ids

    To get information about an IAM role 以下get-role命令获取有关名为Test-Role的角色的信息:

    aws iam get-role --role-name Test-Role
    

    输出:

    {
        "Role": {
            "AssumeRolePolicyDocument": "<URL-encoded-JSON>",
            "RoleId": "AIDIODR4TAW7CSEXAMPLE",
            "CreateDate": "2013-04-18T05:01:58Z",
            "RoleName": "Test-Role",
            "Path": "/",
            "Arn": "arn:aws:iam::123456789012:role/Test-Role"
        }
    }
    

    重要说明基本上,当您使用CloundFront API创建Origin Access Identity时,您将获得UserID和S3规范ID,您必须记下它以在条件字符串中使用它 . http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/private-content-restricting-access-to-s3.html#private-content-creating-oai-api如果您目前没有ID对于CloudFront的Origin Access Identity,请创建一个新的,您可以按照建议保存ID元素和S3 Canonical ID .

  • 0

    我的老答案会支持一些人,但可能不是你的 . 所以,我正在发布另一个答案,它将更准确地满足您的需求 . 以下角色策略将允许访问IAM角色和OAI,并将拒绝其他所有人:

    {
        "Version": "2012-10-17",
        "Statement": [
            {
                "Sid": "1",
                "Effect": "Allow",
                "Principal": {
                    "AWS": "arn:aws:iam::cloudfront:user/CloudFront Origin Access Identity EXXXXXXXXX"
                },
                "Action": "s3:GetObject",
                "Resource": "arn:aws:s3:::bucketname/*"
            },
            {
                "Sid": "2",
                "Effect": "Deny",
                "NotPrincipal": {
                    "AWS": [
                        "arn:aws:iam::cloudfront:user/CloudFront Origin Access Identity EXXXXXXXXX",
                        "arn:aws:iam::AWS-account-ID:role/role-name"
                    ]
                },
                "Action": "s3:GetObject",
                "Resource": "arn:aws:s3:::bucketname/*"
            }
        ]
    }
    
  • 0

    您的问题可以通过将 Deny 语句中的 Principal: "*" 替换为引用CloudFront OAI的相应 NotPrincipal ,并为CloudFront OAI添加适当的 Allow 语句来解决:

    {
      "Version": "2012-10-17",
      "Statement": [
        {
          "Effect": "Deny",
          "NotPrincipal": {
            "CanonicalUser": "..."
          },
          "Action": "s3:*",
          "Resource": [
            "arn:aws:s3:::myBucket",
            "arn:aws:s3:::myBucket/*"
          ],
          "Condition": {
            "StringNotLike": {
              "aws:userId": [
                "MY_IAM_ROLE_USER_ID:*"
              ]
            }
          }
        },
        {
          "Effect": "Allow",
          "Principal": {
            "CanonicalUser": "..."
          },
          "Action": "s3:GetObject",
          "Resource": "arn:aws:s3:::myBucket/*"
        }
      ]
    }
    

    这样,您的IAM角色将被 aws:userId 条件排除在 Deny 语句之外,而您的CloudFront OAI将被 NotPrincipal 条件排除 . 所有其他主体仍将被拒绝访问,CloudFront OAI将仅具有您在存储桶策略中直接授予它的权限 .

    回想起来似乎很简单,这个解决方案当然不是很明显,对于这个答案应该归功于AWS Support,他最近为我回答了同样的问题 .

相关问题