如何使用 S3 预签名 POST url?
How to use an S3 pre-signed POST url?
其实我是第一次使用s3上传文件。我听说过预签名 urls 但显然,我无法设置文件大小限制,所以我发现“预签名 post urls" 但它有点奇怪!!令人惊讶的是我没有找到任何示例。也许这不是我想要的。
我正在从服务器获得预签名 post url:
const { S3 } = require("aws-sdk");
const s3 = new S3({
accessKeyId: accessKey,
secretAccessKey: secretKey,
endpoint: api,
s3ForcePathStyle: true,
signatureVersion: "v4",
});
app.post("/get-url", (req, res) => {
const key = `user/${uuri.v4()}.png`;
const params = {
Bucket: "bucketName",
Fields: {
Key: key,
ContentType: "image/png",
},
};
s3.createPresignedPost(params, function (err, data) {
if (err) {
console.error("Presigning post data encountered an error", err);
} else {
res.json({ url: data.url });
}
});
});
奇怪的是,我得到的 url 不像预签名的 url。它只是端点后跟存储桶名称。没有查询参数。没有选择。
你可能猜到了,我不能用这个 url:
await axios.put(url, file, {
headers: {
"Content-Type": "image/png",
},
});
我什至不知道我应该使用 post 还是两个请求。
我都试过了,没有任何反应。也许预签名 post url 不像预签名 url!
至少给我举个例子!我找不到。
您的方向是正确的,但是您需要更改您正在调用的方法。您当前使用的 createPresignedPost() 的 AWS S3 API 文档指出:
Get a pre-signed POST policy to support uploading to S3 directly from an HTML form.
尝试将此方法更改为 getSignedUrl():
Get a pre-signed URL for a given operation name.
const params = { Bucket: 'bucket', Key: 'key' };
s3.getSignedUrl('putObject', params, function (err, url) {
if (err) {
console.error("Presigning post data encountered an error", err);
} else {
res.json({ url });
}
});
或同步:
const params = { Bucket: 'bucket', Key: 'key' };
const url = s3.getSignedUrl('putObject', params)
res.json({ url });
或者,通过执行 getSignedUrlPromise():
使用承诺
Returns a 'thenable' promise that will be resolved with a pre-signed URL for a given operation name.
const params = { Bucket: 'bucket', Key: 'key' };
s3.getSignedUrlPromise('putObject', params)
.then(url => {
res.json({ url });
}, err => {
console.error("Presigning post data encountered an error", err);
});
另请阅读 API 文档的注释部分,以确保您了解每种方法的局限性。
其实我是第一次使用s3上传文件。我听说过预签名 urls 但显然,我无法设置文件大小限制,所以我发现“预签名 post urls" 但它有点奇怪!!令人惊讶的是我没有找到任何示例。也许这不是我想要的。
我正在从服务器获得预签名 post url:
const { S3 } = require("aws-sdk");
const s3 = new S3({
accessKeyId: accessKey,
secretAccessKey: secretKey,
endpoint: api,
s3ForcePathStyle: true,
signatureVersion: "v4",
});
app.post("/get-url", (req, res) => {
const key = `user/${uuri.v4()}.png`;
const params = {
Bucket: "bucketName",
Fields: {
Key: key,
ContentType: "image/png",
},
};
s3.createPresignedPost(params, function (err, data) {
if (err) {
console.error("Presigning post data encountered an error", err);
} else {
res.json({ url: data.url });
}
});
});
奇怪的是,我得到的 url 不像预签名的 url。它只是端点后跟存储桶名称。没有查询参数。没有选择。
你可能猜到了,我不能用这个 url:
await axios.put(url, file, {
headers: {
"Content-Type": "image/png",
},
});
我什至不知道我应该使用 post 还是两个请求。
我都试过了,没有任何反应。也许预签名 post url 不像预签名 url!
至少给我举个例子!我找不到。
您的方向是正确的,但是您需要更改您正在调用的方法。您当前使用的 createPresignedPost() 的 AWS S3 API 文档指出:
Get a pre-signed POST policy to support uploading to S3 directly from an HTML form.
尝试将此方法更改为 getSignedUrl():
Get a pre-signed URL for a given operation name.
const params = { Bucket: 'bucket', Key: 'key' };
s3.getSignedUrl('putObject', params, function (err, url) {
if (err) {
console.error("Presigning post data encountered an error", err);
} else {
res.json({ url });
}
});
或同步:
const params = { Bucket: 'bucket', Key: 'key' };
const url = s3.getSignedUrl('putObject', params)
res.json({ url });
或者,通过执行 getSignedUrlPromise():
使用承诺Returns a 'thenable' promise that will be resolved with a pre-signed URL for a given operation name.
const params = { Bucket: 'bucket', Key: 'key' };
s3.getSignedUrlPromise('putObject', params)
.then(url => {
res.json({ url });
}, err => {
console.error("Presigning post data encountered an error", err);
});
另请阅读 API 文档的注释部分,以确保您了解每种方法的局限性。