Firebase功能即将消失,没有任何解释或错误

时间:2019-05-16 12:19:01

标签: firebase google-cloud-firestore google-cloud-functions

我正在尝试使用Firebase Firestore和Firebase Cloud Functions实施消息传递应用程序。

从本质上讲,聊天消息作为单独的文档存储在子集合中。最初,我将其实现为直接从客户端添加文档,并在发生更改时侦听集合并更新客户端,但后来我决定切换到使用Cloud函数,以便可以添加一些更好在服务器上完成的功能侧面(过滤等)。

因此,我创建了一个用于发送消息的功能,当用户从应用程序调用该功能时(即,点击发送按钮),该功能将代表用户创建文档。

该功能正常工作,我能够通过日志监视过程。不幸的是,这些功能开始消失而没有错误,控制台报告该功能已成功执行,通常只需不到一秒钟即可执行。

我怀疑这与可能会继续执行的承诺有关,但是这与今天一直有效但失败的代码相同。

如果再尝试几次,这些功能似乎又能正常工作了。我需要保持功能“温暖”吗?云功能是否不够可靠,无法处理此类任务?当我向用户说一条消息已发送时,我需要能够确认该消息已发送,并在失败时与用户进行通信。

很难调试该问题,因为没有引发任何错误(甚至没有信息消息,就好像没有发生一样),它只是说该函数成功完成了执行并且什么也没发生。

我在这里错过了什么吗?谢谢。

exports.sendMessage = functions.https.onCall((data, context) => {
  if (context.auth.uid == undefined) {
    console.warn("SEND MESSAGE: USER NOT SIGNED IN");
    return;
  }

  console.log("Sending message:", data)
  const matchId = data["matchId"];
  const message = data["message"]
  const uid = context.auth.uid

  admin.firestore().collection(MatchingUsers).doc(matchId).collection(UserMessages).add({
    type: "text",
    from: uid,
    message: message,
    timestamp: admin.firestore.Timestamp.now()
  }).then(result => {
    console.log("Message sent")
  }).catch(err => {
    console.log("Error sending mesage:", err)
  })
})

1 个答案:

答案 0 :(得分:2)

HTTP Callable Cloud Functions文档中所述:

  

要在异步操作后返回数据,请返回promise。

然后按照一个示例:

const sanitizedMessage = sanitizer.sanitizeText(text); // Sanitize the message.
return admin.database().ref('/messages').push({
  text: sanitizedMessage,
  author: { uid, name, picture, email },
}).then(() => {
  console.log('New Message written');
  // Returning the sanitized message to the client.
  return { text: sanitizedMessage };
})

因此,您需要按以下方式修改代码:

exports.sendMessage = functions.https.onCall((data, context) => {
  if (context.auth.uid == undefined) {
    console.warn("SEND MESSAGE: USER NOT SIGNED IN");
    //Here send back an error as explained here: https://firebase.google.com/docs/functions/callable#handle_errors
  }

  console.log("Sending message:", data)
  const matchId = data["matchId"];
  const message = data["message"]
  const uid = context.auth.uid

  //Note the return on next line
  return admin.firestore().collection(MatchingUsers).doc(matchId).collection(UserMessages).add({
    type: "text",
    from: uid,
    message: message,
    timestamp: admin.firestore.Timestamp.now()
  }).then(result => {
    console.log("Message sent");
    return { text: "Message sent" };
  }).catch(err => {
    console.log("Error sending mesage:", err);
    //Here, again, send back an error as explained here: https://firebase.google.com/docs/functions/callable#handle_errors
  })
})

如果您不想将值返回给客户端,则可以执行以下操作,当null异步方法返回的Promise解析后,返回add()。 (未经测试,但应该可以使用。)

exports.sendMessage = functions.https.onCall((data, context) => {
  if (context.auth.uid == undefined) {
    console.warn("SEND MESSAGE: USER NOT SIGNED IN");
    return null;
  }

  console.log("Sending message:", data)
  const matchId = data["matchId"];
  const message = data["message"]
  const uid = context.auth.uid

  //Note the return on next line
  return admin.firestore().collection(MatchingUsers).doc(matchId).collection(UserMessages).add({
    type: "text",
    from: uid,
    message: message,
    timestamp: admin.firestore.Timestamp.now()
  }).then(result => {
    console.log("Message sent");   //Actually, if you don't need this console.log() you can remove this entire then() block, returning the promise from add() is enough
    return null;
  }).catch(err => {
    console.log("Error sending mesage:", err);
    return null;
  })
})