【问题标题】:Is there a way to update a flatlist when there's a change in firestore database?当firestore数据库发生变化时,有没有办法更新平面列表?
【发布时间】:2020-03-13 12:33:32
【问题描述】:

我有一个列表,其中显示了用户个人资料、姓名和最后发送的消息。几乎以常规消息传递应用程序显示用户的方式。我要做的是在显示的用户发生变化时更新列表。我尝试让它在渲染时更新,但在重置状态时,它进入一个无限循环,在几秒钟内将我的读取操作提高到 10k。到目前为止,我已经通过拉动刷新来更新它,但我希望它能够实时更新。我不确定是否需要使用云功能(例如 onCreate)或计时器来避免快速超过我的配额限制。

import React, { Component } from "react";
import { View, FlatList } from "react-native";
import { ListItem } from "react-native-elements";
import fireStoreDB from "../database/FirestoreDB";

export default class Home extends Component {
  constructor(props) {
    super(props);
    this.state = {
      usersInfo: [],
      refreshing: false
    };
  }

  componentDidMount() {
    this.LoadUsers();
  }

  LoadUsers = () => {
    fireStoreDB
      .getAllUsersExceptCurrent()
      .then(
        users =>
          Promise.all(
            users.map(
              ({ id, username, avatar }) =>
                fireStoreDB
                  .getUserLastMessage(fireStoreDB.getUID, id)
                  .then(message => ({ id, username, avatar, message }))
            )
          )
      )
      .then(users => {
        this.setState({
          usersInfo: users.filter(x => typeof x.avatar !== "undefined"),
          refreshing: false
        });
      });
  };

  renderItem = ({ item }) => (
    <ListItem
      onPress={() => {
        this.props.navigation.navigate("Chat", {
          userTo: item.id,
          UserToUsername: item.username,
          LoadUsers: this.LoadUsers
        });
      }}
      title={item.username}
      subtitle={item.message}
      leftAvatar={{ source: { uri: item.avatar } }}
      bottomDivider
      chevron
    />
  );

  render() {
    return (
      <View>
        <FlatList
          data={this.state.usersInfo}
          renderItem={this.renderItem}
          keyExtractor={item => item.id}
          refreshing={this.state.refreshing}
          onRefresh={() => {
            this.setState({ refreshing: true });
            this.LoadUsers();
          }}
        />
      </View>
    );
  }
}

【问题讨论】:

  • 您可以在 Firestone 收藏中使用实时事件
  • @Hurobaki 谢谢,我使用 onSnapshot 监听器让它工作。
  • @CLUTCHER,很高兴您能够找到解决问题的方法。请将其作为答案发布并接受它作为解决方案,因为这将有助于其他正在寻找相同问题的社区成员。
  • @AndreiCusnir 我已经发布了我的解决方案。

标签: reactjs firebase react-native google-cloud-firestore react-native-elements


【解决方案1】:

我通过这样做解决了它。

  async componentDidMount() {
    await Font.loadAsync({
      "open-sans-semi-bold": require("../assets/fonts/OpenSans-SemiBold.ttf"),
      Roboto: require("../node_modules/native-base/Fonts/Roboto.ttf"),
      Roboto_medium: require("../node_modules/native-base/Fonts/Roboto_medium.ttf"),
      ...Ionicons.font
    });

    this.unsubscribeMsg = fireStoreDB.lastMsgListener(this.LoadUsers);
    this.unsubscribeUser = fireStoreDB.userProfileListener(this.LoadUsers);
    this.setState({ isReady: true });
  }

  componentWillUnmount() {
    this.unsubscribeUser();
    this.unsubscribeMsg();
  }

  lastMsgListener = loadUsersCallback => {
    return firebase
      .firestore()
      .collectionGroup("chats")
      .onSnapshot(() => {
        loadUsersCallback();
      });
  };

  userProfileListener = loadUsersCallback => {
    return firebase
      .firestore()
      .collection("users")
      .onSnapshot(() => {
        loadUsersCallback();
      });
  };

【讨论】:

  • CLUTCHER 非常感谢您提供该问题的完整解决方案。也请尽快接受它作为解决方案。这将为社区的其他成员提供更多的问题和答案的可见性。
  • LoadUsers 方法在哪里?
  • 嗨 CLUTCHER,希望你很好,我想知道你能帮我解决这个问题吗,真的需要帮助。 stackoverflow.com/questions/65786115/…
猜你喜欢
  • 1970-01-01
  • 2022-10-24
  • 1970-01-01
  • 2019-04-29
  • 2020-02-28
  • 2017-11-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多