【发布时间】: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