【问题标题】:Aws S3 AccessDenied: when uploading objectAws S3 AccessDenied:上传对象时
【发布时间】:2021-07-30 17:19:25
【问题描述】:

我有一个名为 MyBucket 的 s3 存储桶。

权限如下:

存储桶策略:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": "*",
            "Action": "s3:GetObject",
            "Resource": [
                "arn:aws:s3:::MyBucket/files/*"
            ]
        }
    ]
}

在存储桶内,我有一个名为 files 的文件夹。在files内,对象可以被公众查看

对于 IAM 用户,我在下面附加了一个内联策略:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "s3:PutObject",
                "s3:PutObjectAcl",
                "s3:GetObject",
                "s3:DeleteObject"
            ],
            "Resource": "arn:aws:s3:::MyBucket/files/*"
        }
    ]
}

当我使用 nodejs 将对象上传到存储桶时:

s3.upload({
            ACL: 'public-read',
            Bucket: this.app.settings.aws.s3.bucket,
            Body: bufferFromFile,
            Key: `files/${result.id}/${data.fileName}`,
        }, {}).promise();

我收到AccessDenied: Access Denied 错误。

如何解决?

更新 1:

我尝试在评论建议的存储桶策略中添加s3:PutObject,但错误仍然相同。
我正在使用 EC2 来托管 nodejs 代码

更新 2
我尝试使用下面的 CLI 将对象上传到存储桶,它可以工作。

aws s3 cp s3Test.html s3://MyBucket/files/

更新 3

aws s3api put-object --bucket MyBucket --key files/s3Test.html --body s3Test.html --acl public-read

An error occurred (AccessDenied) when calling the PutObject operation: Access Denied

更新 4

只需意识到同一 IAM 用户中可能存在另一个可能相关的托管策略。

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "VisualEditor0",
            "Effect": "Allow",
            "Action": [
                "s3:GetAccessPoint",
                "s3:PutAccountPublicAccessBlock",
                "s3:GetAccountPublicAccessBlock",
                "s3:ListAllMyBuckets",
                "s3:ListAccessPoints",
                "s3:ListJobs",
                "s3:CreateJob",
                "s3:HeadBucket"
            ],
            "Resource": "*"
        },
        {
            "Sid": "VisualEditor1",
            "Effect": "Allow",
            "Action": "s3:*",
            "Resource": [
                "arn:aws:s3:::MyBucket",
                "arn:aws:s3:*:*:accesspoint/*",
                "arn:aws:s3:::*/*",
                "arn:aws:s3:*:*:job/*"
            ]
        }
    ]
}

不确定此政策是否会影响问题。

【问题讨论】:

  • 您的 s3.upload 实际上使用 IAM 用户的凭证和该策略?
  • @Marcin 这是真的
  • 存储桶加密了吗?
  • 你为什么使用--acl public-read?你不阻止吗?没有它还能用吗?
  • 严重...使用 CloudTrail 查找被拒绝的实际请求。日志可能需要一段时间才能通过,但它会提供有价值的信息。您甚至可以尝试运行 aws iam get-user 来确认 IAM 认为您是谁,并且您可以从 Node 调用类似的代码进行比较。仅供参考,--body s3Test.html 只会通过s3Test.html,而不是文件,但这对于测试目的来说很好(通常使用--body file://s3Test.html)。使用 --acl public-read 会公开每个上传的对象,您可能不想这样做,因为您有存储桶策略。

标签: node.js amazon-web-services amazon-s3


【解决方案1】:

从代码中删除ACL: 'public-read' 后它可以工作。

@Marcin 和@John Rotenstein 提供了很好的洞察力和方向,可以在评论中找到原因。真的很感激!

s3.upload({
            ACL: 'public-read', //remove this line
            Bucket: this.app.settings.aws.s3.bucket,
            Body: bufferFromFile,
            Key: `files/${result.id}/${data.fileName}`,
        }, {}).promise();

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-09-04
    • 1970-01-01
    • 2019-03-11
    • 2016-12-21
    • 2019-06-10
    • 1970-01-01
    相关资源
    最近更新 更多