Обновление - похоже, что многие из этих проблем могут быть решены с помощью скрытой переменной process.env.FUNCTION_NAME
, как показано здесь: https://github.com/firebase/functions-samples/issues/170#issuecomment-323375462
Обновление с кодом. Например, если у вас есть следующий индексный файл:
...
exports.doSomeThing = require('./doSomeThing');
exports.doSomeThingElse = require('./doSomeThingElse');
exports.doOtherStuff = require('./doOtherStuff');
// and more.......
Затем будут загружены все ваши файлы, и все эти файлы 'требования также будут загружены, что приведет к большому количеству накладных расходов и загрязнению вашей глобальной области для всех ваших функций.
Вместо разделения ваши значения включают в себя:
if (!process.env.FUNCTION_NAME || process.env.FUNCTION_NAME === 'doSomeThing') {
exports.doSomeThing = require('./doSomeThing');
}
if (!process.env.FUNCTION_NAME || process.env.FUNCTION_NAME === 'doSomeThingElse') {
exports. doSomeThingElse = require('./doSomeThingElse');
}
if (!process.env.FUNCTION_NAME || process.env.FUNCTION_NAME === 'doOtherStuff') {
exports. doOtherStuff = require('./doOtherStuff');
}
Это будет загружать только требуемый файл (ы), когда эта функция специально вызвана; позволяя вам сохранить свою глобальную область намного чище, что должно привести к более быстрым холодным ботинкам.
Это должно обеспечить гораздо более аккуратное решение, чем то, что я сделал ниже (хотя приведенное ниже объяснение по-прежнему сохраняется ).
Оригинальный ответ
Похоже, что требуемые файлы и общая инициализация, происходящие в глобальном масштабе, являются огромной причиной замедления во время холодовой загрузки.
Поскольку проект получает больше функций, глобальная область все больше загрязняется, что делает проблему еще хуже - особенно если вы раскрываете свои функции в отдельные файлы (например, используя Object.assign(exports, require('./more-functions.js'));
в вашем index.js
.
Мне удалось добиться огромных успехов в производительности холодовой загрузки, переместив все мои требования в метод init, как показано ниже, а затем назвал его первой линией внутри любого определения функции для этого файла. Например:
const functions = require('firebase-functions');
const admin = require('firebase-admin');
// Late initialisers for performance
let initialised = false;
let handlebars;
let fs;
let path;
let encrypt;
function init() {
if (initialised) { return; }
handlebars = require('handlebars');
fs = require('fs');
path = require('path');
({ encrypt } = require('../common'));
// Maybe do some handlebars compilation here too
initialised = true;
}
Я видел улучшения от примерно 7-8 до 2-3 лет при применении этого метода к проекту с ~ 30 функциями по 8 файлам. Это также, по-видимому, вызывает необходимость в функциях
К сожалению, это по-прежнему делает HTTP-функции едва пригодными для использования с использованием пользователя.
Надеясь, что команда Firebase имеет некоторые планы в будущем позволяют правильно определять функции, чтобы для каждой функции приходилось загружать только соответствующие модули.