【问题标题】:Data from firestore doesn't get fetched in realtime in useEffect来自 firestore 的数据不会在 useEffect 中实时获取
【发布时间】:2021-07-30 09:02:13
【问题描述】:

我目前正在使用 React Native 和 Expo 编写聊天应用程序,但在实时接收消息时(如果消息被更新、删除或编辑),但它不是实时执行的,它会获取数据,如果我打开聊天页面,但之后不再更新

接收消息:

const [Messages, setMessages] = useState([]);
var TmpMessages = [];

useEffect(() => {
    const messages = () => { 
      firebase.firestore().collection('Users').doc(`${user.uid}`).collection('Friends')
      .doc(`${data.Friend.FriendId}`).collection('Messages').orderBy('Index').onSnapshot(ss => {
        var changes = ss.docChanges();

        // Parsing the messages
        for (var i = 0; i < changes.length; i++) {
            const message = changes[i].doc.data();
            if (changes[i].type == 'added') {
              if (i == 0) message.BeforeAt = 'first message';
              if (message.Sender == user.uid) {
                if (i > 0) {
                  var beforeMessage = changes[i - 1].doc.data();
                  message.BeforeAt = beforeMessage.SendAt;
                  if (beforeMessage.Sender == user.uid) {
                    message.Type = 'SenderBottom';
                  } else {
                    message.Type = 'Sender';
                  }
                } else {
                  message.Type = 'Sender';
                }
              } else {
                if (i > 0) {
                  var beforeMessage = changes[i - 1].doc.data();
                  message.BeforeAt = beforeMessage.SendAt;
                  if (beforeMessage.Sender == data.Friend.FriendId) {
                    message.Type = 'ReceiverBottom';
                  } else {
                    message.Type = 'Receiver';
                  }
                } else {
                  message.Type = 'Receiver';
                }
              }
              TmpMessages.push(message);
            } else if (changes[i].type == 'removed') {
              for (var k = 0; k < TmpMessages.length; k++) {
                if (TmpMessages[k].Id == message.Id) {
                  console.log(message.Id + ' got deleted')
                  TmpMessages.splice(k, 1);
                }
              }
            } else if (changes[i].type == 'updated') {
              for (var k = 0; k < TmpMessages.length; k++) {
                if (TmpMessages[k].Id == message.Id) {
                  console.log(message.Id + ' got updated')
                  TmpMessages[k].Message = message.Message;
                }
              }
            }
          }
          
          setMessages(TmpMessages);
      });
    }

    // Unsubscribe from events when no longer in use
      return () => messages();
  }, []);

这是我的 FlatList:

<FlatList
   style={{ marginBottom: 60, }}
   renderItem={({ item }) => {
      return (
         <ChatItem MessageData={{
            content: item.Message,
            beforeSendAt: item.BeforeAt,
            sendAt: item.SendAt,
         }} MsgType={item.Type} />
      );
   }}
   data={Messages}
   extraData={Messages}
   keyExtractor={(item, index) => index.toString()}
/>

编辑:如果我不将我的 Firebase 事件侦听器放在 useEffect 中,那么它会执行无限循环并最终崩溃。

编辑 2:不要怪我解析消息的代码不够高效,现在它只是概念证明

【问题讨论】:

    标签: javascript firebase react-native google-cloud-firestore


    【解决方案1】:

    我建议每次发生变化时使用整个结果。喜欢这里:

    db.collection("cities").where("state", "==", "CA")
        .onSnapshot((querySnapshot) => {
            var cities = [];
            querySnapshot.forEach((doc) => {
                cities.push(doc.data().name);
            });
            console.log("Current cities in CA: ", cities.join(", "));
        });
    

    而不是ss.docChanges()。只需遍历所有消息。无论如何,您都可以将它们添加到带有 setMessages(TmpMessages); 的状态中。这样你就不需要为所有的变化而烦恼。使用.data(),如果有任何变化,您就可以获得所有这些。

    【讨论】:

    • 感谢它的工作!我只需要更改一些代码以匹配我的代码就可以了!
    猜你喜欢
    • 2021-07-27
    • 2020-07-25
    • 2021-10-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-02-06
    • 2021-12-31
    • 1970-01-01
    相关资源
    最近更新 更多