【发布时间】:2021-06-30 19:34:35
【问题描述】:
我有一个 API 调用的 lambda,它生成签名的 getObject 和 putObject URL。我的受限存储桶(包含 zip 文件)上的 GET 和 PUT 工作正常,但我的公共存储桶(包含图像)上的 PUT 会返回“SignatureDoesNotMatch”错误。公共存储桶上没有 GET,直接引用来自该存储桶的图像。我是否需要额外的配置才能将 PUT 放在公共存储桶上?我已经尝试过给予我能想到的最慷慨的权限。
编辑:我最终不得不将特定图像 MIME 类型发送到生成签名 URL 的端点。不幸的是,image/* 不起作用。
签名 URL 生成(由 getSignedImgUploadUrl 调用)
let params = {
Bucket: "public-bucket",
Key: `${folder}/${key}.jpg`, // Ideally without extension
Expires: 30,
ContentType: "image/jpeg", // Ideally image/*
ACL: "public-read" // Tried with and without this
};
let url = s3.getSignedUrl("putObject", params);
let result = {
signedUrl: url,
key: key
};
return result;
使用签名网址
public uploadImg(folder: string, file: any, key: string): Observable<any> {
return this._spinnerService.spinObservable(
new Observable(subscriber => {
this.getSignedImgUploadUrl(folder, key)
.subscribe(result => {
// put to signedUrl fails with 403 SignatureDoesNotMatch
this._httpClient.put(result["signedUrl"], file, { headers: { "x-amz-acl": "public-read" } })
.subscribe(() => {
subscriber.next(result["key"]);
subscriber.complete();
}, err => {
console.log(err);
subscriber.error(err);
});
}, err => {
console.log(err);
subscriber.error(err);
});
}));
}
Lambda 角色
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "VisualEditor0",
"Effect": "Allow",
"Action": [
"s3:PutObject",
"s3:GetObject"
],
"Resource": "arn:aws:s3:::restricted-bucket/*"
},
{
"Sid": "VisualEditor1",
"Effect": "Allow",
"Action": [
"s3:ListAllMyBuckets"
],
"Resource": "*"
},
{
"Sid": "VisualEditor2",
"Effect": "Allow",
"Action": "s3:*", (Ideally just getObject/putObject)
"Resource": "arn:aws:s3:::public-bucket/*"
}
]
}
公共存储桶政策
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "PublicReadGetObject",
"Effect": "Allow",
"Principal": "*",
"Action": "s3:GetObject",
"Resource": "arn:aws:s3:::public-bucket/*"
},
// Also tried adding s3:* for the lambda role without luck
{
"Sid": "Stmt1624999949645",
"Effect": "Allow",
"Principal": {
"AWS": "arn:aws:iam::account:role/service-role/lambda-role"
},
"Action": "s3:*",
"Resource": "arn:aws:s3:::public-bucket/*"
}
]
}
【问题讨论】:
-
能否也显示上传对象的代码?
-
当然!我从 UI 添加了代码,我首先在其中获取签名的 url,然后尝试将图像放入其中。我最近尝试使用 acl 标头,但这并没有什么不同。
-
尝试在客户端显式发送
Content-Type标头。 -
嗯......这完全有效。为什么您认为公共存储桶/图像类型需要 Content-Type 客户端而不是 zips?
标签: amazon-web-services amazon-s3 aws-lambda