【问题标题】:AWS S3 Bucket policiesAWS S3 存储桶策略
【发布时间】:2018-03-25 04:57:00
【问题描述】:

我创建了一个带有 cloudformation 的存储桶:

AWSTemplateFormatVersion: "2010-09-09"
Parameters:
  BucketName:  
    Type: String
    Description: "Choose a name for the S3 Bucket"
    Default: "myrandomnameforbucket"
  S3Bucket:
    Type: "AWS::S3::Bucket"
    Properties:
      AccessControl: "Private"
      BucketName: !Ref BucketName

现在我正在编写一个 bucketPolicy,但我遇到了一些问题。我想要达到的目标:

  • 用户 A (UserA) 可以上传到 S3
  • 用户 A (UserA) 无法从 S3 中删除
  • 所有用户(在我的环境中,不公开)都可以从 S3 读取
  • 所有用户(在我的环境中,nob public)都可以从 S3 中删除

我怎样才能做到这一点? 目前我拒绝从 userA 删除并允许从 userA 上传。

          - Effect: Deny
            Principal:
              AWS: 
                !GetAtt UserA.Arn
            Action: "s3:DeleteObject"
            Resource: 
              Fn::Join:  ["", ["arn:aws:s3:::", Ref: "S3Bucket", "/*"]]
          - Effect: Allow
            Principal:
              AWS: 
                !GetAtt UserA.Arn
            Action: "s3:PutObject"
            Resource: 
              Fn::Join:  ["", ["arn:aws:s3:::", Ref: "S3Bucket", "/*"]]
          - Effect: Allow
            Principal: "?" # * is public?
            Action: s3:GetObject
            Resource: 
              Fn::Join:  ["", ["arn:aws:s3:::", Ref: "S3Bucket", "/*"]]

【问题讨论】:

    标签: amazon-web-services amazon-s3 amazon-cloudformation


    【解决方案1】:

    我知道有两个问题:

    1. 如何在排除匿名用户时向所有 IAM 用户授予访问权限
    2. 如何限制一个用户多于其他用户,即:删除您刚刚授予他人的权限

    第一个问题一开始听起来很简单,就像the documentation states

    在基于资源的策略中,使用 Principal 元素指定允许访问资源的帐户或用户

    所以这意味着你可以这样做:

    Principal:
        AWS: !Ref "AWS::AccountId"
    

    但是当我尝试它时它不起作用。设置特定用户的 arn 时,它对我有用。这对我来说似乎是一个错误。或者文档中的不明确。有this other report I found

    无论如何,您可以使用Principal: AWS: "*",然后使用Conditionrestrict to IAM users only

    第二个问题要简单得多:评估策略时明确的denys 优先于一般的allows、see documentation

    生成的策略可以是例如写成这样:

    S3Policy:
      Type: "AWS::S3::BucketPolicy"
      Properties:
        Bucket: !Ref S3Bucket
        PolicyDocument:
          Statement:
            - Effect: Deny
              Action: "s3:DeleteObject"
              Resource: !Join ["", ["arn:aws:s3:::", Ref: "S3Bucket", "/*"]]
              Principal:
                AWS: !GetAtt UserA.Arn
            - Effect: Allow
              Action: "s3:PutObject"
              Resource: !Join ["", ["arn:aws:s3:::", Ref: "S3Bucket", "/*"]]
              Principal:
                AWS: !GetAtt UserA.Arn
            - Effect: Allow
              Action: ["s3:GetObject", "s3:DeleteObject"]
              Resource: !Join ["", ["arn:aws:s3:::", Ref: "S3Bucket", "/*"]]
              Principal:
                AWS: "*"
              Condition:
                StringEquals:
                  "aws:PrincipalType": ["User"]
    

    【讨论】:

      【解决方案2】:
        {
      "Version": "2012-10-17",
      "Id": "S3PolicyId1",
      "Statement": [
          {
              "Sid": "AllowGet",
              "Effect": "Allow",
              "Principal":{"AWS":"arn:aws:iam::account-number-without-hyphens:user/user1"},
              "Action": [
                  "s3:Get*",
                  "s3:List*"
              ],
              "Resource": [
                  "arn:aws:s3:::s3_bucket_name",
                  "arn:aws:s3:::s3_bucket_name/*"
              ]
          },
          {
              "Sid": "DenyDeleteObject",
              "Effect": "Deny",
              "Principal": {"AWS":"arn:aws:iam::account-number-without-hyphens:user/user1"},
              "Action": "s3:Delete*",
              "Resource": [
                  "arn:aws:s3:::s3_bucket_name",
                  "arn:aws:s3:::s3_bucket_name/*"
              ]
          },
          {
              "Sid": "Allow anyone in your account to access bucket",
              "Effect": "Allow",
              "Principal": {
                  "AWS": "arn:aws:iam::account-number-without-hyphens:root"
              },
              "Action": [
                  "s3:Get*",
                  "s3:List*",
                  "s3:Put*",
                  "s3:Delete*"
              ],
              "Resource": [
                  "arn:aws:s3:::s3_bucket_name",
                  "arn:aws:s3:::s3_bucket_name/*"
              ]
          }
      ]
      

      }

      这是我快速整理的 JSON 格式的模板。我在这里的假设是您的组“所有用户(在我的环境中,nob public)”是帐户中的每个人。因此,我们在第三个块中定义它。你可以随心所欲地操纵主体。

      如果您有任何问题,请提出,我很乐意提供帮助。

      【讨论】:

      • 你试过了吗?我刚刚在这方面工作了一段时间,显然基于帐户的委托人在 s3 策略中不起作用。另请参阅此线程:forums.aws.amazon.com/thread.jspa?messageID=838365&#838365
      • 你想跨账户吗?如果没有,您可以拒绝一切,只允许特定用户或角色执行某些操作。在您的情况下,什么是组?
      • 这在使用相同的帐户帐户 ID 时也不起作用。 IMO 唯一的方法是使用 IAM 策略并将其分配给一个组
      • 有趣。在那种情况下,我相信 IAM 是唯一的选择。但是,对存储桶的显式拒绝不起作用,这听起来很奇怪。我需要对此进行试验。
      • 看起来有一组模板可以帮助你 -> gist.github.com/actionjack/d900c6587297f24d83b14c2b7a85200f
      猜你喜欢
      • 1970-01-01
      • 2019-04-24
      • 2012-11-23
      • 2017-02-14
      • 2018-08-09
      • 1970-01-01
      • 1970-01-01
      • 2011-09-10
      • 1970-01-01
      相关资源
      最近更新 更多