javascript - functions - Habilitación de CORS en funciones en la nube para Firebase
firebase functions tutorial (12)
Actualmente estoy aprendiendo a usar nuevas funciones de nube para Firebase y el problema que tengo es que no puedo acceder a la función que escribí a través de una solicitud AJAX. Me sale el error "No ''Access-Control-Allow-Origin''". Aquí hay un ejemplo de la función que escribí:
exports.test = functions.https.onRequest((request, response) => {
response.status(500).send({test: ''Testing functions''});
})
La función se encuentra en esta url: https://us-central1-fba-shipper-140ae.cloudfunctions.net/test
Firebase docs sugiere agregar el middleware CORS dentro de la función, lo he probado pero no funciona para mí: https://firebase.google.com/docs/functions/http-events
Así es como lo hice:
var cors = require(''cors'');
exports.test = functions.https.onRequest((request, response) => {
cors(request, response, () => {
response.status(500).send({test: ''Testing functions''});
})
})
¿Qué estoy haciendo mal? Agradecería cualquier ayuda con esto.
ACTUALIZAR:
La respuesta de
Doug Stevenson
ayudó.
Al agregar ({origin: true}) se solucionó el problema, también tuve que cambiar
response.status(500)
a
response.status(200)
que me perdí por completo al principio.
Acabo de publicar un pequeño artículo sobre eso:
https://mhaligowski.github.io/blog/2017/03/10/cors-in-cloud-functions.html
En general, debe usar el paquete Express CORS , que requiere un poco de pirateo para cumplir con los requisitos de las funciones GCF / Firebase.
¡Espero que ayude!
Esto puede ser útil. Creé la función de nube HTTP firebase con express (URL personalizada)
const express = require(''express'');
const bodyParser = require(''body-parser'');
const cors = require("cors");
const app = express();
const main = express();
app.post(''/endpoint'', (req, res) => {
// code here
})
app.use(cors({ origin: true }));
main.use(cors({ origin: true }));
main.use(''/api/v1'', app);
main.use(bodyParser.json());
main.use(bodyParser.urlencoded({ extended: false }));
module.exports.functionName = functions.https.onRequest(main);
Asegúrese de agregar secciones de reescritura
"rewrites": [
{
"source": "/api/v1/**",
"function": "functionName"
}
]
Hay dos funciones de muestra proporcionadas por el equipo de Firebase que demuestran el uso de CORS:
La segunda muestra usa una forma diferente de trabajar con cors que la que está usando actualmente.
Además, considere importar de esta manera, como se muestra en las muestras:
const cors = require(''cors'')({origin: true});
Para cualquiera que intente hacer esto en Typecript, este es el código:
import * as cors from ''cors'';
const corsHandler = cors({origin: true});
export const exampleFunction= functions.https.onRequest(async (request, response) => {
corsHandler(request, response, () => {});
//Your code here
});
Por lo que vale, estaba teniendo el mismo problema al pasar la
app
a
onRequest
.
Me di cuenta de que el problema era una barra diagonal en la url de solicitud para la función firebase.
Express estaba buscando
''/''
pero no tenía la barra diagonal final en la función
[project-id].cloudfunctions.net/[function-name]
.
El error CORS fue un falso negativo.
Cuando agregué la barra inclinada final, obtuve la respuesta que esperaba.
Puede configurar el CORS en la función de nube como este
response.set(''Access-Control-Allow-Origin'', ''*'');
No es necesario importar el paquete
cors
Si hay personas como yo: si desea llamar a la función de nube desde el mismo proyecto que la función de nube, puede iniciar el sdk de firebase y usar el método onCall. Se encargará de todo por ti:
exports.newRequest = functions.https.onCall((data, context) => {
console.log(`This is the received data: ${data}.`);
return data;
})
Llame a esta función así:
// Init the firebase SDK first
const functions = firebase.functions();
const addMessage = functions.httpsCallable(`newRequest`);
Documentos de Firebase: https://firebase.google.com/docs/functions/callable
Si no puede iniciar el SDK, aquí está la esencia de las otras sugerencias:
- Si usa el host firebase y el host en la ubicación predeterminada, elija reescrituras: https://firebase.google.com/docs/hosting/full-config#rewrites
- O use CORS como sugirió krishnazden: https://.com/a/53845986/1293220
Si no está utilizando Express o simplemente desea utilizar CORS. El siguiente código ayudará a resolver
const cors = require(''cors'')({ origin: true, });
exports.yourfunction = functions.https.onRequest((request, response) => {
return cors(request, response, () => {
// *Your code*
});
});
Solo de esta manera funciona para mí, ya que tengo autorización en mi solicitud:
exports.hello = functions.https.onRequest((request, response) => {
response.set(''Access-Control-Allow-Origin'', ''*'');
response.set(''Access-Control-Allow-Credentials'', ''true''); // vital
if (request.method === ''OPTIONS'') {
// Send response to OPTIONS requests
response.set(''Access-Control-Allow-Methods'', ''GET'');
response.set(''Access-Control-Allow-Headers'', ''Content-Type'');
response.set(''Access-Control-Max-Age'', ''3600'');
response.status(204).send('''');
} else {
const params = request.body;
const html = ''some html'';
response.send(html)
} )};
Tengo una pequeña adición a la respuesta de @Andreys a su propia pregunta.
Parece que no tiene que llamar a la devolución de llamada en la función
cors(req, res, cb)
, por lo que puede llamar al módulo cors en la parte superior de su función, sin incrustar todo su código en la devolución de llamada.
Esto es mucho más rápido si desea implementar cors después.
exports.exampleFunction = functions.https.onRequest((request, response) => {
cors(request, response, () => {});
return response.send("Hello from Firebase!");
});
No olvides iniciar los cors como se menciona en el post de apertura:
const cors = require(''cors'')({origin: true});
Una información adicional, solo por el bien de aquellos que buscan en Google después de un tiempo: si está utilizando Firebase Hosting, también puede configurar reescrituras, de modo que, por ejemplo, una URL como (firebase_hosting_host) / api / myfunction redirija a ( función firebase_cloudfunctions_host) / doStuff. De esa manera, dado que la redirección es transparente y del lado del servidor, no tiene que lidiar con cors.
Puede configurar eso con una sección de reescrituras en firebase.json:
"rewrites": [
{ "source": "/api/myFunction", "function": "doStuff" }
]
Ninguna solución CORS funcionó para mí ... ¡hasta ahora!
No estoy seguro de si alguien más se encontró con el mismo problema que yo, pero configuré CORS como 5 formas diferentes de los ejemplos que encontré y nada parecía funcionar. Configuré un ejemplo mínimo con Plunker para ver si realmente era un error, pero el ejemplo funcionó muy bien. Decidí revisar los registros de funciones de Firebase (que se encuentran en la consola de Firebase) para ver si eso podría decirme algo. Tuve un par de errores en mi código de servidor de nodo , no relacionados con CORS , que cuando depuré me liberaron de mi mensaje de error CORS . No sé por qué los errores de código no relacionados con CORS devuelven una respuesta de error CORS, pero me llevaron por el agujero de conejo equivocado durante un buen número de horas ...
tl; dr: verifique los registros de funciones de firebase si no hay soluciones CORS que funcionen y depure cualquier error que tenga