Javascript Firebase onWrite cloud功能不会间歇运行

Javascript Firebase onWrite cloud功能不会间歇运行,javascript,firebase,firebase-realtime-database,google-cloud-functions,firebase-queue,Javascript,Firebase,Firebase Realtime Database,Google Cloud Functions,Firebase Queue,多年来,我一直在使用firebase queue来调用作业,但最近它开始失败,事务错误与资源竞争,并且存在严重的扩展问题 因此,我将firebase queue迁移到了云函数,最初它看起来很快,而且非常可扩展。我在queue/task/{taskId}上编写了一个由onWrite连接的简单脚本。但有时onWrite似乎从来都不是随机触发的。我根本看不到日志中触发的特定作业 我们正在使用blaze plan,函数返回承诺,时间限制设置为最大值,99.9%的作业占用时间小于5000毫秒 我们每天大约

多年来,我一直在使用
firebase queue
来调用作业,但最近它开始失败,事务错误与资源竞争,并且存在严重的扩展问题

因此,我将
firebase queue
迁移到了云函数,最初它看起来很快,而且非常可扩展。我在
queue/task/{taskId}
上编写了一个由onWrite连接的简单脚本。但有时onWrite似乎从来都不是随机触发的。我根本看不到日志中触发的特定作业

我们正在使用blaze plan,函数返回承诺,时间限制设置为最大值,99.9%的作业占用时间小于5000毫秒

我们每天大约有5万次调用,大约有100个作业没有被触发。这是如此断断续续,没有任何线索。奇怪的是,我在日志查看器上没有看到任何错误,但在调用图上,我可以看到一些加载错误和连接错误,但仍然不知道它们是什么。如有任何解决问题的见解,将不胜感激

const functions = require(`firebase-functions`);
const admin = require(`firebase-admin`);
const _ = require(`lodash`);
const specs = require(`./specs.json`);
const queueSpecs = require(`./queue-specs.js`);

const SERVER_TIMESTAMP = { ".sv": `timestamp` };

admin.initializeApp();

const workers = {};

queueSpecs.forEach((spec) => {
    let specString = spec;

    if (typeof spec === `object`) {
        specString = spec.id;
    }

    workers[specString] = require(`./lib/workers/${specString}`);
});

const taskHandler = (change, context) => {
    const data = change.after.val();
    const ref = change.after.ref;
    const { taskID } = context.params;

    if (!data) {
        return null;
    }

    const worker = workers[data._state];

    if (!worker) {
        console.error(`Worker not found for task ${taskID} - ${data._state}`);
        return null;
    }

    const specID = data._state.replace(`/`, `_`);
    const spec = specs[specID];

    if (!spec) {
        console.error(`Spec not found for task ${taskID} - ${specID}`);
        return null;
    }

    console.log(
        `Running ${taskID} - ${data._state} - ${JSON.stringify(data, null, 2)}`
    );

    return new Promise((resolve, reject) => {
        const taskResolve = newTask => {
            const updates = _.clone(newTask);
            let newState = _.get(newTask, `_new_state`, ``);

            newState = newState || spec.finished_state;

            if (!updates || !newState) {
                console.log(`Exiting task - ${taskID}`);
                return ref.set(null).then(resolve, reject);
            }

            updates._state = newState || spec.finished_state;
            updates._state_changed = SERVER_TIMESTAMP;
            updates._owner = null;
            updates._progress = null;
            updates._error_details = null;

            console.log(`Resolving`);

            return ref.update(updates).then(resolve, reject);
        };

        const taskReject = error => {
            const updates = {};
            let errorString;

            if (_.isError(error)) {
                errorString = error.message;
            } else if (_.isString(error)) {
                errorString = error;
            } else if (!_.isUndefined(error) && !_.isNull(error)) {
                errorString = error.toString();
            }

            if (updates._state === `error`) {
                console.log(`Exiting task on reject - ${taskID}`);
                return ref.set(null).then(resolve, reject);
            }

            updates._state = spec.error_state || `error`;
            updates._state_changed = SERVER_TIMESTAMP;
            updates._owner = null;
            updates._progress = null;
            updates._error_details = {
                previous_state: spec.in_progress_state,
                error: errorString,
                errorStack: _.get(error, `stack`, null),
                attempts: 1
            };

            console.log(`Rejecting`);
            return ref.update(updates).then(resolve, reject);
        };

        const taskProgress = () => {
            // eslint-disable-line
            // progress is never used, thus just resolving
            const updates = {};

            console.log(`Progress ????`);

            return ref.update(updates).then(resolve, reject);
        };

        worker(data, taskProgress, taskResolve, taskReject);
    });
};

exports.taskRunner = functions.database
    .ref(`/queue/tasks/{taskID}`)
    .onWrite(taskHandler);

堆栈溢出无法使用此级别的信息帮助您调试函数。您应该1)发布您的特定代码并说明其工作方式与您期望的不同,或者2)联系Firebase支持人员,提供您的特定观察结果,表明您的函数没有按照您期望的频率执行。1) 如果我知道代码的哪一部分导致了这种情况,我不会在这里发布。2) 我在问社区是否有其他人也有同样的问题,所以我不认为这是离题。添加了代码片段。如果你问的是关于Firebase产品的可靠性或稳定性的一般性问题,而不涉及代码,最好在Firebase talk上问。