如何使用带有CORS的Go API返回的SignedURL?
当前设置:
Bucket配置
gsutil cors get gs://example-bucket
收益:
[{
"maxAgeSeconds": 1,
"method": ["GET", "HEAD", "PUT", "DELETE", "POST", "OPTIONS"],
"origin": ["http://example.com", "https://example.com", "http://localhost:4000"],
"responseHeader": ["Origin", "Accept", "X-Requested-With", "Authorization", "Content-Type", "Content-Length", "Accept-Encoding", "X-CSRF-Token"
]}]
去API调用
acc, _ := appengine.ServiceAccount(ctx)
signedUrl, err := storage.SignedURL(
"example-bucket",
fileName,
&storage.SignedURLOptions{
GoogleAccessID: acc,
SignBytes: func(b []byte) ([]byte, error) {
_, signedBytes, signingError := appengine.SignBytes(ctx, b)
return signedBytes, signingError
},
Method: "PUT",
ContentType: contentType,
Expires: time.Now().Add(1 * time.Hour),
})
JS XHR
使用Go的SignedURL,即xhr.open("PUT", signedUrl);
附注
SignURL是由Go API生成的,总是以https://storage.googleapis.com/example-bucket/fileName
开头...在其他地方我已经读过它应该是www.googleapis.com/storage
但我不认为这是问题,肯定从官方API返回的url是正确的。
我可以看到请求标头包括:
access-control-request-headers: content-type,x-upload-content-type
access-control-request-method: PUT
origin: http://localhost:4000
所以它似乎勾掉了所需标题的所有方框......
在JS方面,我通过X-Upload-Content-Type
标头为文件上传设置了额外的元数据。
由于此标头不在CORS配置中,因此请求失败。
通过将该标头添加到配置中(例如,提供给responseHeader
配置文件的gsutil cors set
列表),一切都正如问题中描述的那样工作:)