问题
For my project, I have a requirement to upload pdf into the s3 bucket. So using a lambda function I create a pre-signed URL and using the url i use http post request to upload the file.
Now, with the pre-signed link i received from the lambda function, it is possible to upload the file using POSTMAN without any, but in my angular Application, for some reason i get a 403(Forbidden) Error.
Here are all my code:
Lambda Function
async function getSignedUrlForResume(fileName){
const urlExpiryDuration = 5; //minutes
console.log("inside get signed Url");
const key = "Resume/"+fileName;
var response = "";
const s3Params ={
Bucket: process.env.S3_BUCKET_NAME,
Key: key,
Expires: urlExpiryDuration*60,
ACL: 'public-read',
ContentType: "application/pdf"
};
const s3 = new AWS.S3();
try {
const signedUrl = await s3.getSignedUrl('putObject', s3Params);
response = {signedUrl: signedUrl};
return response;
} catch (error) {
response = error;
return response;
}
}
Component.ts File:
async addResume(){
let signedUrl : string = null;
let fileName: string = this.candidateService.candidateRecords['records'][this.candidateService.indexOfCandidate]['candidate_id']
+"_"+
this.candidateService.candidateRecords['records'][this.candidateService.indexOfCandidate]['first_name']
+"_"+
this.candidateService.candidateRecords['records'][this.candidateService.indexOfCandidate]['last_name'];
console.log("File Name: " +fileName);
this.file = event[0];
await this.candidateService.getSignedUrl(fileName).then(
(response: []) => {
signedUrl = response['signedUrl'];
}
);
console.log(signedUrl);
console.log(this.file)
await this.candidateService.uploadResume(signedUrl, this.file).then
(data => {
console.log("Upload Response:" +data);
}).catch((err: Error) => {
console.log('Error: '+ err);
});
}
Component Service
getSignedUrl(fileName: string){
let queryParams = new HttpParams();
queryParams = queryParams.set('fileName', fileName).set('funcName', 'getSignedUrlForResume');
return this.http.get(AppConstants._API_END_URL, {params: queryParams})
.pipe(
retryAfterDelay(this.delayDuration),
catchError((errorResponse:Error) => {
return throwError(errorResponse.message);
}
)
).toPromise();
}
uploadResume(signedUrl: string, file: File){
// Delay not added for upload to s3. since no RDS is used
return this.http.put(signedUrl, file, {headers: {'Content-Type': file.type}}).toPromise();
}
}
HTML part:
<input hidden type="file" #fileInput (change)="uploadFile($event.target.files)" accept="application/pdf">
ERROR:
"<?xml version="1.0" encoding="UTF-8"?>
<Error><Code>AccessDenied</Code><Message>There were headers present in the request which were not signed</Message><HeadersNotSigned>x-amz-security-token</HeadersNotSigned><RequestId>E841149CC447C62D</RequestId></Error>"
Can anyone point out what i am doing wrong here or not done to make this work ??
来源:https://stackoverflow.com/questions/65225397/aws-s3-403forbidden-error-in-angular-app-during-file-upload