Подтвердить что ты не робот

Включение CORS в облачных функциях для Firebase

В настоящее время я изучаю, как использовать новые функции Cloud для Firebase, и проблема, с которой я сталкиваюсь, заключается в том, что я не могу получить доступ к функции, которую я написал через запрос AJAX. Я получаю ошибку "Нет" Access-Control-Allow-Origin ". Вот пример функции, которую я написал:

exports.test = functions.https.onRequest((request, response) => {
  response.status(500).send({test: 'Testing functions'});
})

Функция находится в этом URL: https://us-central1-fba-shipper-140ae.cloudfunctions.net/test

Firebase docs предлагает добавить промежуточное ПО CORS внутри функции, я пробовал, но он не работает для меня: https://firebase.google.com/docs/functions/http-events p >

Вот как я это сделал:

var cors = require('cors');    

exports.test = functions.https.onRequest((request, response) => {
   cors(request, response, () => {
     response.status(500).send({test: 'Testing functions'});
   })
})

Что я делаю неправильно? Я был бы признателен за любую помощь в этом.

UPDATE:

Даг Стивенсон помог. Добавление ({origin: true}) устранило проблему, мне также пришлось изменить response.status(500) на response.status(200), который я полностью пропустил вначале.

4b9b3361

Ответ 1

Существуют две примеры функций, предоставленные командой Firebase, которые демонстрируют использование CORS:

Во втором примере используется другой способ работы с cors, чем вы в настоящее время используете.

Кроме того, рассмотрите импортирование, подобное этому, как показано в примерах:

const cors = require('cors')({origin: true});

Ответ 2

Вы можете установить CORS в облачной функции следующим образом: response.set('Access-Control-Allow-Origin', '*'); Нет необходимости импортировать пакет cors

Ответ 3

Для тех, кто пытается сделать это в Typescript, это код:

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
});

Ответ 4

Один дополнительный фрагмент информации, только ради того, чтобы зайти через это через некоторое время: Если вы используете хостинг firebase, вы также можете настроить перезаписи, чтобы, например, URL-адрес (firebase_hosting_host)/api/myfunction перенаправлялся на функцию (firebase_cloudfunctions_host)/doStuff. Таким образом, поскольку перенаправление прозрачное и серверное, вам не нужно иметь дело с cors.

Вы можете установить это с помощью раздела перезаписи в файле firebase.json:

"rewrites": [
        { "source": "/api/myFunction", "function": "doStuff" }
]

Ответ 5

У меня есть небольшое дополнение к @Andreys, отвечающему на его собственный вопрос.

Кажется, вам не нужно вызывать обратный вызов в функции cors(req, res, cb), поэтому вы можете просто вызвать модуль cors в верхней части своей функции, не вставляя весь свой код в обратный вызов. Это намного быстрее, если вы захотите впоследствии реализовать корс.

exports.exampleFunction = functions.https.onRequest((request, response) => {
    cors(request, response, () => {});
    return response.send("Hello from Firebase!");
});

Не забывайте инициализировать корс, как указано в открытии сообщения:

const cors = require('cors')({origin: true});

Ответ 6

Никакие решения CORS не работали для меня... до сих пор!

Не уверен, сталкивался ли кто-нибудь еще с той же проблемой, что и я, но я настроил CORS, как 5 разных способов по сравнению с примерами, которые я нашел, и ничего не получалось. Я создал минимальный пример с Plunker, чтобы увидеть, действительно ли это было ошибкой, но пример прошел прекрасно. Я решил проверить журналы функций firebase (найденные в консоли firebase), чтобы узнать, может ли это сказать мне что-нибудь. У меня была пара ошибок в моем коде сервера узлов, не связанных с CORS, которые, когда я отлаживал, освободили меня от моего сообщения об ошибке CORS. Я не знаю, почему ошибки кода, не связанные с CORS, возвращают ответ об ошибке CORS, но это привело меня к неправильной кроличьей норе на целое количество часов...

tl; dr - проверяет ваши журналы Firebase-функций, если не работают решения CORS, и отлаживает любые ваши ошибки

Ответ 7

Я только что опубликовал небольшой фрагмент:

https://mhaligowski.github.io/blog/2017/03/10/cors-in-cloud-functions.html

Как правило, вы должны использовать Express пакет CORS, что требует небольшого взлома, чтобы соответствовать требованиям в функциях GCF/Firebase.

Надеюсь, что это поможет!

Ответ 8

Для чего это стоило у меня onRequest такая же проблема при передаче app в onRequest. Я понял, что проблема заключалась в косой черте в URL запроса для функции firebase. Express искал '/' но у меня не было косой черты в функции [project-id].cloudfunctions.net/[function-name]. Ошибка CORS была ложноотрицательной. Когда я добавил косую черту, я получил ожидаемый ответ.

Ответ 9

Только этот способ работает для меня, так как у меня есть авторизация в моем запросе:

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)
} )};

Ответ 10

Это может быть полезно. Я создал Firebase HTTP функцию облака с экспресс (пользовательский URL)

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);

Пожалуйста, убедитесь, что вы добавили переписать разделы

"rewrites": [
      {
        "source": "/api/v1/**",
        "function": "functionName"
      }
]

Ответ 11

Если вы не используете Express или просто хотите использовать CORS. Следующий код поможет решить

const cors = require('cors')({ origin: true, });   
exports.yourfunction = functions.https.onRequest((request, response) => {  
   return cors(request, response, () => {  
        // *Your code*
    });
});

Ответ 12

Если есть такие люди, как я: если вы хотите вызвать облачную функцию из того же проекта, что и сама облачная функция, вы можете запустить firebase sdk и использовать метод onCall. Он будет обрабатывать все для вас:

exports.newRequest = functions.https.onCall((data, context) => {
    console.log('This is the received data: ${data}.');
    return data;
})

Вызовите эту функцию следующим образом:

// Init the firebase SDK first    
const functions = firebase.functions();
const addMessage = functions.httpsCallable('newRequest');

Документы Firebase: https://firebase.google.com/docs/functions/callable

Если вы не можете инициировать SDK, вот суть из других предложений: