Closed kuldeeppoonia closed 7 years ago
The browser will need to set the matching Content Type on the request headers.
As needed. If you provide a content-type, the client (browser) must provide this HTTP header set to the same value. - https://cloud.google.com/storage/docs/access-control/signed-urls
If you remove the content type while creating the signed URL, it should work in the browser.
Thanks a lot
Hi ,
I am using latest 'aws-java-sdk-s3', version: '1.11.158'. I am getting below error when uploading the files. I am able to list the buckets. Is there any signature setting I have do.?
The request signature we calculated does not match the signature you provided. Check your Google secret key and signing method. com.amazonaws.services.s3.model.AmazonS3Exception: The request signature we calculated does not match the signature you provided. Check your Google secret key and signing method. (Service: Amazon S3; Status Code: 403; Error Code: SignatureDoesNotMatch; Request ID: null), S3 Extended Request ID: null
Hi, there!
I'm facing the same problem but I've already removed the content type while creating the signed URL. The interesting fact is that this problem only happens suddenly a few days after the signed URL is created..
The code I'm following is the one below: https://github.com/firebase/functions-samples/blob/master/generate-thumbnail/functions/index.js
Thanks in advance!
I notice the example code sets the expiration date for 482 years from now, so that's probably not the issue :) (Unless-- did you change it?)
Assuming that's not the case, I'm not sure what it could be. Could you open a new issue on the https://github.com/firebase/functions-samples repo? If it turns out to be a problem with our library, we can continue to look at it and see what we can do.
I'm getting the same error. I do not pass content-type to signer method. Do I need to set some special permissions on the bucket maybe, have an ACL or something? Service Account that is used to sign urls has Storage Admin role.
Same as @jayarjo here.
Also, the file I'm trying to access have a name like Customers/{id}/kitten.jpeg
. I use all this name to get my signedUrl, and not only kitten.jpeg
(makes sense to me).
Is there any further explanations here ?
Can someone provide solution for this. URL worked for few days after geenration now suddenly my android app is not able to download image and it fails with "HttpException: Invalid statusCode: 403,". From browser it gives below error
`This XML file does not appear to have any style information associated with it. The document tree is shown below.
SignatureDoesNotMatch
Have the same problem :)
export async function storeFileInStorage(filename: string, objectId: string, fileType: FileType, base64Content: Buffer, objectType: string): Promise<FileInfo> {
const folderName = objectType === "PROFILE" ? `profiles` : `agreements`;
const bucket = admin.storage().bucket();
const fileAsByteArray = new Uint8Array(base64Content);
const bucketFilename = folderName + "/" + objectId + "/" + fileType + "_" + filename;
const file = bucket.file(bucketFilename);
let publicUrl;
await file.save(fileAsByteArray)
.then(async stuff => {
publicUrl = await file.getSignedUrl({
action: "read",
expires: "05-09-2999"
});
}).catch(err => {
throw Error("Could not store file for objectId: ${objectId} with to ${bucketFilename} error: ${err}");
});
return {publicUrl: publicUrl ?? "", storagePath: bucketFilename, type: fileType};
}
For example url
Can someone suggest something?
Greetings folks! If you're having issues, please open a new issue here: https://github.com/googleapis/nodejs-storage/
For me it was because I was using POST instead of PUT, it's not just about the ContentType header, the http method also has to match, in golang:
method := "PUT" // THIS MUST MATCH
expires := time.Now().Add(time.Minute * 10)
url, err := storage.SignedURL(bucket, filename, &storage.SignedURLOptions{
GoogleAccessID: cfg.Email,
PrivateKey: cfg.PrivateKey,
Method: method,
Expires: expires,
ContentType: "binary/octet-stream", // NOTE
})
if err != nil {
// ...
}
var client = http.DefaultClient
request, err := http.NewRequest("PUT", url, req.Body) // we use PUT not POST
if err != nil {
// ....
}
request.Header.Set("Content-Type", "binary/octet-stream") // this must match
response, err := client.Do(request)
I'm in the same boat, uploaded image's url works but some days later, getting 403.
found suspicious note about expires
parameter on the api doc:
A timestamp when this link will expire. Any value given is passed to new Date(). Note: 'v4' supports maximum duration of 7 days (604800 seconds) from now.
If anyone ever encounters this error again, in my case the key had an expiry date and it had expired. Generating a new key worked
I am having the same issue today: we're the 9th of August 2023, and here are the parameters: X-Goog-Date=20230803T154108Z&X-Goog-Expires=604800
The link should be valid until the 10th, but somehow I am getting Access Denied with SignatureDoesNotMatch.
For some reasons this link was working for a few days and now stopped working before expiration date.
I am generating the link using firebase admin in a Cloud run environment:
const thumbnailUrlExpiresAt = new Date(Date.now() + 604800000); // 7 days
const [signedUrl] = await firebase
.storage()
.bucket(process.env.BUCKET_VIDEO_THUMBNAILS)
.file(lastExport.thumbnailData?.thumbnailPath)
.getSignedUrl({
version: 'v4',
action: 'read',
expires: thumbnailUrlExpiresAt
});
What is actually going on here?
Also, please note that I am also saving the expiration Date of that link in my database and it is set to 2023-08-10T15:41:08.412+00:00
@jayarjo @JustinBeckwith @stephenplusplus @schankam I have the same issue index.js
const { onRequest } = require('firebase-functions/v2/https');
const webhookHandler = require('./webhook');
const getTransactionDetails = require('./getTransactionDetails');
exports.webhookHandler = onRequest(webhookHandler);
exports.getTransactionDetails = onRequest(getTransactionDetails);
webhook.js
const getFirebaseApp = require('./firebaseConfig');
const { getFirestore } = require('firebase-admin/firestore');
const { onRequest } = require('firebase-functions/v2/https');
const firebaseApp = getFirebaseApp();
exports.saveTransactionDetails = onRequest(async (req, res) => {
try {
console.log(req);
console.log('req body is', req.body);
const total = parseFloat(req.body.total) || 0;
const counter = parseInt(req.body.counter) || 0;
const db = getFirestore();
const totalsRef = db.collection('totals').doc('total');
const totalsDoc = await totalsRef.get();
if (totalsDoc.exists) {
const totalsData = totalsDoc.data();
const newTotal = totalsData.total + total;
const newCounter = totalsData.counter + counter;
await totalsRef.update({
total: newTotal,
counter: newCounter
});
} else {
await totalsRef.set({
total,
counter
});
}
res.status(200).json({ message: 'Transaction details saved successfully' });
} catch (error) {
res.status(500).json({ message: 'Failed to save transaction details' });
}
});
getTransactionDetails.js
const getFirebaseApp = require('./firebaseConfig');
const { getFirestore } = require('firebase-admin/firestore');
const { onRequest } = require('firebase-functions/v2/https');
const firebaseApp = getFirebaseApp();
exports.getTransactionDetails = onRequest(async (req, res) => {
try {
const db = getFirestore();
const totalsRef = db.collection('totals').doc('total');
const totalsDoc = await totalsRef.get();
if (totalsDoc.exists) {
const totalsData = totalsDoc.data();
res.status(200).json({ total: totalsData.total, counter: totalsData.counter });
} else {
res.status(404).json({ message: 'Transaction details not found' });
}
} catch (error) {
res.status(500).json({ message: 'Failed to retrieve transaction details' });
}
});
Firebaseconfig.js
const { initializeApp } = require('firebase-admin/app');
let firebaseApp;
function getFirebaseApp() {
if (!firebaseApp) {
firebaseApp = initializeApp();
}
return firebaseApp;
}
module.exports = getFirebaseApp;
Hi team, I have spent a lot of time to solve the problem and also spent a lot of time to search the solution on net but every time I failed. The scenario is that
I am using @google-cloud/storage to upload my image on google cloud storage. Everything is fine. Images successfully uploaded on cloud. Now I want to show these images to my users but I didn't want to give public permission to images. So I created a signed url and trying to download them but everytime I am facing the following problem
here is my code
But when I put this signed url in browser it give me the error.
I am following the url for uploading image https://googlecloudplatform.github.io/google-cloud-node/#/docs/storage/0.6.0/storage
How ever I can download these image in nodejs using file.download() but I want to view this image on browser
Please guide me when am I wrong.