【发布时间】:2018-02-27 15:58:50
【问题描述】:
真的在这个问题上苦苦挣扎,所以任何帮助都会很棒!
所以我尝试使用预签名的 url 直接从浏览器将 pdf 文件上传到 Amazon S3。
我使用 AWS Java SDK(用 Kotlin 编写的代码)在服务器上生成 url,如下所示:
val objectKey = StringBuilder().append("xxx").append("/").append("file1.pdf").toString()
val expiration = java.util.Date()
var msec = expiration.time
msec += (1000 * 60).toLong() // Add 1 minute. This means that the url expires in 1 minute.
expiration.time = msec
String bucketName = "test"
val responseHeaders = ResponseHeaderOverrides().withContentType("multipart/form-data")
val generatePresignedUrlRequest = GeneratePresignedUrlRequest(bucketName, objectKey)
generatePresignedUrlRequest.method = HttpMethod.POST
generatePresignedUrlRequest.responseHeaders = responseHeaders
generatePresignedUrlRequest.expiration = expiration
return s3Client.generatePresignedUrl(generatePresignedUrlRequest)
这个 url 然后返回给使用 Angular 的浏览器代码。 然后我使用以下打字稿代码直接上传文件:
returnPresignUrl() {
return this.http.get(this.attachmentUploadUrl, this.httpOptions);
}
uploadFiletoS3(file, filetype) {
let presignURL;
const data = file;
const fileHeaders = {
headers: new HttpHeaders({
'Content-Type': 'multipart/form-data',
})
};
this.returnPresignUrl().subscribe(url => {
presignURL = url;
this.http.post(presignURL, data,
fileHeaders).subscribe((res) => {
console.log('File uploaded', res);
}, (error) => { console.log('Error uploading File', error);
});
}, (error) => { console.log('Error getting a preasign URL: ',
error); });
}
但我得到以下错误响应:
<Code>SignatureDoesNotMatch</Code>
<Message>
The request signature we calculated does not match the signature you
provided. Check your key and signing method.
</Message>
有什么想法吗?
我在 presign url 中指定内容类型标头,然后还在对 url 的发布请求中设置它,所以我看不到标头不匹配的情况(一个似乎导致问题的错误我看到了)。
发帖请求有什么特别之处吗? 将 pdf 文件上传到 S3 的内容类型是否正确?
任何见解都会很棒,谢谢!
【问题讨论】:
-
您能检查一下您的访问密钥和密钥吗?当您的密钥也无效时,您会收到此错误。
-
Java SDK 表示应该使用 setMethod(HttpMethod 方法),支持的方法有 GET、PUT、DELETE、HEAD。使用放置。此外,通常您可能应该使用 setResponseHeaders() 之类的 setter 方法。
-
当我将其更改为 PUT 时,我收到拒绝访问错误。有任何想法吗?访问密钥和密钥不应该包含在其中,因为使用预签名 URL 的全部意义在于我们不需要在浏览器中存储安全凭证。
-
另外,这是 Kotlin 代码,记住,直接引用字段并设置它与调用 set() 方法相同
-
好的,现在你得到了 AccessDenied,你已经解决了最初的问题。您的预签名 URL 是否过期?客户端时间同步了吗?
标签: angular amazon-web-services amazon-s3 kotlin pre-signed-url