Access Control Allow Origin on Safari
Hello, how is everything? Could you help me, please?
I'm having problems using Cloudinary API directly from the frontend.
In some browsers I'm just getting CORS error.
"https://api.mydomain.com.br is not allowed by Access-Crontrol-Allow-Origin"
It works fine on Chrome and Mozilla on Ubuntu but crashes on Chrome and Safari for MacOS.
Could you help me, please?
I'm signing the parameters in my backend and only after requesting the API directly from the Frontend
Here's the code I'm using.
Backend for signing:
const getSignature = async (req, res, next) => {
const timestamp = Math.round(new Date().getTime() / 1000);
console.log("Getting Signature_secret", config.CLOUDNARY_API_SECRET);
const params = {
timestamp: timestamp,
...req.query,
};
console.log("Getting Signature", params);
const CloudnarySignature = await cloudinary.utils.api_sign_request(
params,
config.CLOUDNARY_API_SECRET
);
res.json({
sucesso: true,
params: { ...req.query, timestamp },
api_key: config.CLOUDNARY_API_KEY,
timestamp,
signature: CloudnarySignature,
});
};
And the Frontend code:
const uploadCardVideos = (nextVideo) => {
return new Promise((resolve, reject) => {
const public_id = nextVideo.attachmentId;
const eager = "sp_full_hd_lean/m3u8";
const notification = "https://api.mydomain.com.br/api/uploaded";
const paramsToSign = `public_id=${public_id}&eager=${eager}&eager_notification_url=${notification}&eager_async=true`;
const cloudname = process.env.REACT_APP_CLOUDNARY_CLOUDNAME
const apiKey = process.env.REACT_APP_CLOUDNARY_API_KEY
// GET THE SIGNED PARAMS
uploadCloud(paramsToSign).then((responseFromServer) => {
// FETCH KEYS THEN
const ts = responseFromServer.timestamp;
const sig = responseFromServer.signature;
const endpoint = `https://api.cloudinary.com/v1_1/${cloudname}/video/upload?api_key=${apiKey}×tamp=${ts}&signature=${sig}&${paramsToSign}`;
const formData = newFormData();
const file = nextVideo.file;
formData.append("file", file);
fetch(endpoint, {
method: "POST",
body: formData,
}).then((response) => {
return response.text();
}).then((data) => {
const response=JSON.parse(data);
if (response&&response.eager&&response.eager.length>-1) {
const insertion= {
acessor: nextVideo.acessor,
id: nextVideo.attachmentId,
uploaded: true,
hosted: true,
status: response.eager[0].status,
original: nextVideo.file.name,
path: response.secure_url,
type: "video",
url: response.eager[0].secure_url,
};
console.log("UPLOAD_FLUX_UPLOADED", insertion);
resolve(insertion);
return true;
} else {
console.log("UPLOAD_FLUX_ERROR", response);
reject({ error: "upload_error_basic", public_id });
// throw new Error("Failed uploading Cloud");
}
}).catch((err) => {
reject({ error: err, public_id });
});
})
.catch((err) => {
reject({ error: err, public_id });
});
});
};
Sorry for the code formatting is really strange in this editor.
Thank you
-
Hi Juliana,
Thanks for sharing the error and code.
From this, I see that the browser rejected the request and returned this error message when it attempted to make a cross-site request to https://api.mydomain.com.br (which I believe is what you are using to receive the params to sign and return back a signature) and the cross-site request was not for a request to Cloudinary.
It's not clear from the backend code what web framework you're using as it only shows one function, but if you are using Express for example, then you can find out how to enable CORS on your server under the following link:
https://expressjs.com/en/resources/middleware/cors.htmlIf you are not using Express, then the web framework you are using should also be able to support configuring CORS headers and it's worth checking their documentation on the exact ways you can enable that.
Please let us know how it goes.
Best,
Aleksandar0 -
Hello Aleksandar,
Thanks for the answer.Actually the Request is done directly by my Frontend and is being rejected by Cloudinary endpoint: "https://api.cloudinary.com ...."
"mydomain" is just not to expose my domain here in support.
and its used on the query parameter: eager_notification_url=${notification}the Upload is done in Frontend so the error has nothing to do with Express or Backend.
I'm using my Backend just to sign the parameters and get the signature using the official Lib from NPM and this is happening normally.
As I said, the Request works in some browsers, so I think it is the case to add or remove some Header in the request, but this must be done directly in Frontend.
Thank you very much.
0 -
Hi Juliana,
Thanks for your response.
For us to better understand we would need the full error message without any obfuscation.
May I please ask you to submit a ticket with us directly via - https://support.cloudinary.com/hc/en-us/requests/new - and share with us a screenshot of the error or a link to your site which we can use to reproduce the issue?
In general, when we receive an OPTIONS (preflight) request (part of CORS flow) we take the value of the Origin header, which should be added by the browser automatically, and return that as part of theAccess-Control-Allow-Origin
in the response thus allowing the browser to send the subsequent request. Based on the error message you shared earlier, it appears that the preflight OPTIONS request either didn't specify the Origin header or the request header was blank and that would explain why the response from Cloudinary didn't include the "Access-Control-Allow-Origin" response header.Having said this, being able to reproduce the issue would be the quickest way to understand the reason for the error.
Looking forward to your response.
Best,
Aleksandar0
Post is closed for comments.
Comments
3 comments