预签名的 S3 上传 url 在到期时间之前到期

我有一个 lambda 来生成预签名的上传 URL。这是我用来获取 URL 的代码:


    urlExpiresAt := time.Duration(10) * time.Second

    s3Session := s3.New(awsSession)

    request, _ := s3Session.PutObjectRequest(&s3.PutObjectInput{

        Bucket:      aws.String(awssettings.FileStorageBucketName),

        Key:         aws.String(fmt.Sprintf("%s/%s", *cognitoUser.Username, filename)),

        ContentType: aws.String(uploadContentType),

    })


    uploadUrl, err := request.Presign(urlExpiresAt)

在我的前端,我检索该 URL 并立即尝试向它发送上传 POST 请求:


    try {

      const {

        data: { fileUploadUrl },

      } = await graphQlClient.query({

        query: gql(getFileUploadUrlQuery),

        variables: {

          filename,

        },

      });


      const formdata = new FormData();

      formdata.append("file", file);

      const ajaxRequest = new XMLHttpRequest();

      ajaxRequest.upload.addEventListener("progress", progressHandler, false);

      ajaxRequest.addEventListener("load", completeHandler, false);

      ajaxRequest.addEventListener("error", errorHandler, false);

      ajaxRequest.addEventListener("abort", abortHandler, false);

      ajaxRequest.open("POST", fileUploadUrl);

      ajaxRequest.send(formdata);

    } catch (err) {

      console.log(err);

    }

出于测试目的,我将我的存储桶配置为可公开访问:


{

    "Version": "2012-10-17",

    "Statement": [

        {

            "Sid": "UploadFiles",

            "Effect": "Allow",

            "Principal": "*",

            "Action": "s3:PutObject",

            "Resource": "<bucketARN>/*"

        }

    ]

}

用于测试目的的 CORS 配置如下:


[

    {

        "AllowedHeaders": [

            "*"

        ],

        "AllowedMethods": [

            "POST"

        ],

        "AllowedOrigins": [

            "http://localhost:8080"

        ],

        "ExposeHeaders": []

    }

]

CORS 飞行前请求返回状态200,但是POST发送文件内容的请求被拒绝403并出现以下错误:


<Error>

  <Code>AccessDenied</Code>

  <Message>Request has expired</Message>

  <X-Amz-Expires>5</X-Amz-Expires>

  <Expires>2022-09-07T04:14:50Z</Expires>

  <ServerTime>2022-09-13T06:40:18Z</ServerTime>

...

</Error>

阅读此错误,看起来 URL 在预签名之前已过期,这没有意义。


我在这里做错了什么?


暮色呼如
浏览 169回答 1
1回答

侃侃无极

我发现我的解决方案有两个问题:PUT首先,使用方法生成预签名 URL ,而不是POST其次,AWSAppSyncClient我使用 GraphQL 客户端默认缓存查询结果,所以我需要的只是禁用缓存fetchPolicy: "network-only"&nbsp; &nbsp; const {&nbsp; &nbsp; &nbsp; &nbsp; data: { fileUploadUrl },&nbsp; &nbsp; &nbsp; } = await graphQlClient.query({&nbsp; &nbsp; &nbsp; &nbsp; query: gql(getFileUploadUrlQuery),&nbsp; &nbsp; &nbsp; &nbsp; fetchPolicy: "network-only",&nbsp; &nbsp; &nbsp; &nbsp;// <- THIS LINE&nbsp; &nbsp; &nbsp; &nbsp; variables: {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; filename,&nbsp; &nbsp; &nbsp; &nbsp; },&nbsp; &nbsp; &nbsp; });
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go