每个 then() 都应该返回一个值或抛出 Firebase 云函数

IT技术 javascript firebase google-cloud-functions
2021-02-21 02:51:06

我正在使用 javascript 为 firebase 编写云函数,但我被卡住了,我不知道错误的确切含义并且无法解决它..错误状态:27:65 错误每个 then() 应该返回一个值或抛出Promise/总是回报

'use strict'

const functions = require('firebase-functions');
const admin = require('firebase-admin');
admin.initializeApp();

exports.sendNotification = functions.database.ref('/notifications/{user_id}/{notification_id}').onWrite((change, context) => {

    const user_id = context.params.user_id;
    const notification_id = context.params.notification_id;
    console.log('We have a notification from : ', user_id);

    if (!change.after.val()) {
        return console.log('A Notification has been deleted from the database : ', notification_id);
    }
    const deviceToken = admin.database().ref(`/ServiceProvider/${user_id}/device_token`).once('value');
    return deviceToken.then(result => {
        const token_id = result.val();
        const payload = {
            notification: {
              title : "New Friend Request",
              body: "You Have Received A new Friend Request",
              icon: "default"
            }
        };

        return admin.messaging().sendToDevice(token_id, payload).then(response => {

            console.log('This was the notification Feature');

        });

    });

});
3个回答

改变这个:

    return admin.messaging().sendToDevice(token_id, payload).then(response => {

        console.log('This was the notification Feature');

    });

对此:

    return admin.messaging().sendToDevice(token_id, payload).then(response => {

        console.log('This was the notification Feature');
        return null;   // add this line

    });

then回调只需要返回一个值。

然而,eslint 可能会抱怨嵌套then()在你的代码中,这也是一种反模式。你的代码应该更像这样的结构:

const deviceToken = admin.database().ref(`/ServiceProvider/${user_id}/device_token`).once('value');
return deviceToken.then(result => {
    // redacted stuff...
    return admin.messaging().sendToDevice(token_id, payload);
}).then(() => {
    console.log('This was the notification Feature');
});

请注意,每个然后相互链接,而不是相互嵌套。

@DougStevenson 为什么你说“然后回调只需要返回一个值”但你的第二个例子then只有日志功能,没有返回值?
2021-04-17 02:51:06
@YoApps 这个谷歌实验室展示了一个类似的例子来说明你的要求,它也很好developers.google.com/web/ilt/pwa/working-with-promises#catch
2021-05-06 02:51:06
@Doug Stevenson,我为您对 Firebase 的所有贡献鼓掌。但是为什么 Firebase 云函数网站上有这么多地方,他们从来没有正确显示这部分代码。我什至写信到反馈链接来更正代码(在必要时添加额外的回报),就像你在这里显示的那样,但无济于事。
2021-05-09 02:51:06
嘿,谢谢,我已经解决了这个问题,但是如果我的设备此时连接到互联网,fcm 会传递消息,如果我在 30 秒后打开互联网,通知会在某处丢失。
2021-05-14 02:51:06

改变这个:

    return admin.messaging().sendToDevice(token_id, payload).then(response => {

    console.log('This was the notification Feature');

  });

进入这个:

    return admin.messaging().sendToDevice(token_id, payload).then(response=>{
      console.log('This was the notification Feature');
      return true;
    },err=>
    {
      throw err;
    });

正如错误所说,使用时then您需要返回一个值。

“返回”undefined作为then回调的值也一样好(如果你不需要另一个值)。
2021-04-26 02:51:06
没有必要捕获并重新抛出错误。被拒绝的Promise将沿着Promise链一直传播到 Cloud Functions。
2021-05-04 02:51:06
嘿,谢谢,我已经解决了这个问题,但是如果我的设备此时连接到互联网,fcm 会传递消息,如果我在 30 秒后打开互联网,通知会在某处丢失。
2021-05-10 02:51:06

这是 jslinting 告诉您每个.then必须包含一个返回值。换句话说,避免promise 反模式

您可能会发现async函数更容易理解。请注意,您需要运行 Node 8 运行时以获得异步支持...

这不是您链接的Promise构造函数反模式
2021-04-28 02:51:06