javascript - 使用 gcs 上传签名 URL 的图像上传问题 | react JS

标签 javascript reactjs xmlhttprequest google-cloud-storage gsutil

使用它来生成 GCS 上传签名 url v4 https://github.com/GoogleCloudPlatform/python-docs-samples/blob/master/storage/cloud-client/storage_generate_upload_signed_url_v4.py#L27

我已经使用上面提到的这个函数“generate_upload_signed_url_v4”生成了上传签名的 url,我也尝试使用 GSUTIL 以及使用 gsutil signurl -m PUT service_account.json gs://<bucket>/file.png 我正在做一个演示,我需要将 PDF、PNG 上传到 GCS 存储桶。文件上传是文件。但是当我在 GCS 存储控制台中预览文件并下载/预览文件表单链接 URL
PDF 没问题。但是 PNG 以某种方式损坏并且无法打开/预览。 我正在使用 Chrome '81.0.4044.138'

当我使用文本编辑器进一步预览 PNG 文件时,它在文件顶部包含一些标题内容。 IE ------WebKitFormBoundarysZ3BDVaNOhqwENsp Content-Disposition: form-data; name="file"; filename="test.png" Content-Type: image/png 因此,如果我们从文件顶部删除它,文件将正常打开。

我已经创建了一个示例 React 项目,可以在此处访问

演示:https://github.com/qaisershehzad/upload-gcs

我正在使用此代码进行文件上传

` const url = "https://storage.googleapis.com//file.png.png?X-Goog-Algorithm=GOOG4-RSA-SHA256&X-Goog-Credential=gitlab-ci%.iam.gserviceaccount.com%2F20200521%2Fauto%2Fstorage %2Fgoog4_request&X-Goog-Date=20200521T175304Z&X-Goog-Expires=36000&X-Goog-SignedHeaders=content-type%3Bhost&X-Goog-Signature="

const data = new FormData()
data.append('file', this.state.selectedFile)

var xhr = new XMLHttpRequest();

xhr.open('PUT', url, true);
xhr.setRequestHeader("Content-type", "application/octet-stream");


xhr.onload = function (response) {
  console.log('on-load', response);
};

xhr.onreadystatechange = function () {
  if (xhr.readyState === 4) {

    if (xhr.status === 200) {
      console.log("Status OK")

    } else {
      console.log("Status not 200")
    }
  }
};

xhr.onerror = function (response) {
  console.log("Response error", response)
};

xhr.upload.onprogress = function (evt) {
  // For uploads
  if (evt.lengthComputable) {
    var percentComplete = parseInt((evt.loaded / evt.total) * 100);
    console.log("progress", percentComplete)

  }
}
xhr.send(data);`

我也在 Android 上尝试过同样的事情,但遇到了同样的问题。在顶部的 Png 中,添加了这些标题字符串,不允许打开 Png 文件。

使用此 CURL 请求,PNG 上传工作正常。 curl -X PUT -H 'Content-Type: application/octet-stream' --upload-filen file.png ' https://storage.googleapis.com//file.png?X-Goog-Algorithm=GOOG4-RSA-SHA256&X-Goog-Credential=gitlab-ci%.iam.gserviceaccount.com%2F20200521%2Fauto%2Fstorage%2Fgoog4_request&X-Goog-Date=20200521T175304Z&X-Goog-Expires= 36000&X-Goog-SignedHeaders=content-type%3Bhost&X-Goog-Signature='

如果有人可以帮助解决这个问题,那将会很有帮助。

最佳答案

实际上,您正在发送 FormData,这会导致问题,您会看到文件已上传,但当您检索文件时,如果图像可能无法呈现,其内容会有所不同。

cURL 起作用的原因是您直接发送文件而不是 FormData。

要解决此问题,请直接将文件传递给 ajax,如下所述:

const file = this.state.selectedFile;

ajax.setRequestHeader('Content-Type', file.type);    
ajax.send(file); // direct file not FormData

关于javascript - 使用 gcs 上传签名 URL 的图像上传问题 | react JS,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61950270/

相关文章:

javascript - 在ajax响应中获取php超链接的值

javascript - React.js 对对象数组的搜索过滤

javascript - XMLHttpRequest 仅发送最大大小为 130 kB 的文件

javascript - React navigation 5从堆栈导航器中隐藏标签栏

javascript - 为什么 XMLHttpRequest 响应的长度与请求文件的大小不同?

ajax - 跨域 XHR/AJAX : a possible workaround?

javascript - 如何在 Laravel 中拆分或分离序列化表单数据

javascript - 如何将 express.js 服务器部署到 Netlify

javascript - 使用jquery更新字段不会更新可观察的

reactjs - 使用 Jest 和 Enzyme 进行 react 测试 @react-google-maps/api 返回 TypeError : Cannot read property 'maps' of undefined