node.js - 测试 AWS S3 Presigned Url 返回 403 Forbidden (Nodejs)

标签 node.js amazon-web-services amazon-s3 aws-lambda pre-signed-url

我在 API 网关后面有一个 Lambda Nodejs 函数,它成功返回了一个预签名 URL:

const AWS = require('aws-sdk');
const S3 = new AWS.S3({
  apiVersion: '2006-03-01',
  signatureVersion: 'v4'
});

function getSignedUrl(id, type) {
  const key = `uploads/${id}.${type}`;
  return S3.getSignedUrl('putObject', {
    Bucket: 'example-bucket-name',
    Key: key,
    Expires: 300
  });
}

预签名 URL 可能如下所示:

https://example-bucket-name.s3.eu-central-1.amazonaws.com/uploads/489eb7115d0c479eaf9c3b6a01eb1893.png?Content-Type=image%2Fpng&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=ASIARTVN4TPKUACY5POZ%2F20200616%2Feu-central-1%2Fs3%2Faws4_request&X-Amz-Date=20200616T104031Z&X-Amz-Expires=300&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEEMaDGV1LWNlbnRyYWwtMSJHMEUCIQCDd%2B5hFjcBd%2FA6TEV7Se6L%2B6V8VtgCrMg0%2FbOkoGKy1wIgL20u20i%2B80rnBf49MfU1T3MQK2RQdoyQF6SwGQiYgeMq7gEIvP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARABGgwxMTA5NjAwOTAwNjkiDIcy2z8%2FpQIhMOOaZirCAUFhV6uGF%2Ff44lDl%2BaFxIt9D302gcuPaxlrgZWlRMHb%2FEdrKFJsWP%2FG7%2B6ovilKh9WmcBX1fzuVa%2BHQ6rv6OaCueMEnDOBEj%2FvJ1hrI%2FwMDF1RLVlqq7pTDp6h6hmUxPfbqXu1k8sjcFotVzXZTzR0dX6kmWl41uEvaglXjrGG3ApvviH%2BSFLdUdvK9PBgrgSlamGIhxdJN75xxBzQMELfdpPJ6QanhLEwIa%2FuMliHPliXC2fasMzFEheA3Xmik43McnMJ3DovcFOuABdae1G7uUXOSaQzGZ7IjPLLZnMFfow4SzosQHlMUurlqQATPbieC9W3McsMVwggwzZX6BcN9OJb%2B0Ag3x9pS5eLnLsEio%2FyAPZJfXzoGBH5AdZ6TAZtC5cgKy0TEebH%2F3bF4%2FiamoTQ6YcZ4f48NefoNFHcRPXl3VF%2FdINmuTSG1cNlh2svT9jAUfOgaeK7tnFAW79L38Nv7xnnFMYFpyxoUx8XVkffCXmq15dyG7rLIR0FHkJ7p4C8eEqbQzOj%2Fsj1ELFFAWPtq38ZgFnWF%2BYf6W4UrkHD9AGdUucD1qvAA%3D&X-Amz-Signature=e11f346296a979e586b8f81a9db2ef2ce58c9f7a13a4f3c31f9a0bb9997b8b81&X-Amz-SignedHeaders=host

但是,在浏览器中测试所述 URL 时,我得到一个 SignatureDoesNotMatch。我想这似乎很公平,因为我以后只想将它与应用程序中的 PUT 一起使用。

然而,使用 curl 或 postman 我得到 403 Forbidden:
curl -v -X PUT -T 489eb7115d0c479eaf9c3b6a01eb1893.png "https://example-bucket-name.s3.eu-central-1.amazonaws.com/uploads/489eb7115d0c479eaf9c3b6a01eb1893.png?Content-Type=image%2Fpng&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=ASIARTVN4TPKUACY5POZ%2F20200616%2Feu-central-1%2Fs3%2Faws4_request&X-Amz-Date=20200616T104031Z&X-Amz-Expires=300&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEEMaDGV1LWNlbnRyYWwtMSJHMEUCIQCDd%2B5hFjcBd%2FA6TEV7Se6L%2B6V8VtgCrMg0%2FbOkoGKy1wIgL20u20i%2B80rnBf49MfU1T3MQK2RQdoyQF6SwGQiYgeMq7gEIvP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARABGgwxMTA5NjAwOTAwNjkiDIcy2z8%2FpQIhMOOaZirCAUFhV6uGF%2Ff44lDl%2BaFxIt9D302gcuPaxlrgZWlRMHb%2FEdrKFJsWP%2FG7%2B6ovilKh9WmcBX1fzuVa%2BHQ6rv6OaCueMEnDOBEj%2FvJ1hrI%2FwMDF1RLVlqq7pTDp6h6hmUxPfbqXu1k8sjcFotVzXZTzR0dX6kmWl41uEvaglXjrGG3ApvviH%2BSFLdUdvK9PBgrgSlamGIhxdJN75xxBzQMELfdpPJ6QanhLEwIa%2FuMliHPliXC2fasMzFEheA3Xmik43McnMJ3DovcFOuABdae1G7uUXOSaQzGZ7IjPLLZnMFfow4SzosQHlMUurlqQATPbieC9W3McsMVwggwzZX6BcN9OJb%2B0Ag3x9pS5eLnLsEio%2FyAPZJfXzoGBH5AdZ6TAZtC5cgKy0TEebH%2F3bF4%2FiamoTQ6YcZ4f48NefoNFHcRPXl3VF%2FdINmuTSG1cNlh2svT9jAUfOgaeK7tnFAW79L38Nv7xnnFMYFpyxoUx8XVkffCXmq15dyG7rLIR0FHkJ7p4C8eEqbQzOj%2Fsj1ELFFAWPtq38ZgFnWF%2BYf6W4UrkHD9AGdUucD1qvAA%3D&X-Amz-Signature=e11f346296a979e586b8f81a9db2ef2ce58c9f7a13a4f3c31f9a0bb9997b8b81&X-Amz-SignedHeaders=host"

Lambda 函数具有以下权限:
s3:ListBucket          Allow: arn:aws:s3:::example-bucket-name
s3:GetBucketLocation   Allow: arn:aws:s3:::example-bucket-name
s3:PutObject           Allow: arn:aws:s3:::example-bucket-name/uploads/*

S3 存储桶具有以下 CORS 规则:
<?xml version="1.0" encoding="UTF-8"?>
<CORSConfiguration xmlns="http://s3.amazonaws.com/doc/2006-03-01/">
<CORSRule>
    <AllowedOrigin>*</AllowedOrigin>
    <AllowedMethod>HEAD</AllowedMethod>
    <AllowedMethod>GET</AllowedMethod>
    <AllowedMethod>PUT</AllowedMethod>
    <AllowedMethod>POST</AllowedMethod>
    <MaxAgeSeconds>3000</MaxAgeSeconds>
    <ExposeHeader>ETag</ExposeHeader>
    <AllowedHeader>*</AllowedHeader>
</CORSRule>
</CORSConfiguration>

这是存储桶 ACL:
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "AWSConfigBucketPermissionsCheck",
            "Effect": "Allow",
            "Principal": {
                "Service": "config.amazonaws.com"
            },
            "Action": "s3:GetBucketAcl",
            "Resource": "arn:aws:s3:::example-bucket-name"
        },
        {
            "Sid": "DenyUnEncryptedTraffic",
            "Effect": "Deny",
            "Principal": {
                "AWS": "*"
            },
            "Action": "*",
            "Resource": "arn:aws:s3:::example-bucket-name/*",
            "Condition": {
                "Bool": {
                    "aws:SecureTransport": "false"
                }
            }
        }
    ]
}

难道是上面的 DenyUnEncryptedTraffic 规则导致了 403?我通过删除所述规则对其进行了测试,但仍然得到 403。

阻止所有公共(public)访问已开启!

存储桶拥有者拥有存储桶的完全访问权限!

我已经在这方面浪费了太多时间,真的需要一些帮助!

最佳答案

好吧,现在我觉得很愚蠢:

刚刚用 Postman 测试了说 Presigned PUT URL 并且它以某种方式工作:

enter image description here

确保输入预签名 URL,选择 PUT,然后选择二进制并添加文件。

如果有人觉得这很有用,我会留下这个。

关于node.js - 测试 AWS S3 Presigned Url 返回 403 Forbidden (Nodejs),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62407318/

相关文章:

node.js - 错误 : (gcloud. app.deploy)错误响应:[9] 应用程序启动错误:

amazon-web-services - AWS CloudFormation 部署覆盖 "name"标签?

android - 使用云中的VM构建Android自定义ROM

amazon-web-services - 可以向 aws s3 presign url 发送 PUT 请求吗?

javascript - 无法通过 IPP 在另一个纸盘上打印

node.js - 使用 SocketIO 和 Express 进行 Node mocha API 测试

node.js - 面对这个错误 : TypeError: yargs. 命令不是函数

amazon-web-services - 使用一个 cloudFormation 模板从 zip 文件创建一个 lambda 并创建一个 S3 存储桶

css - Django CSS 相对路径在 Amazon S3 中不起作用

meteor - 从 cfs :gridfs to cfs:s3 迁移