【发布时间】:2021-05-26 09:15:11
【问题描述】:
我设置了以下 useEffect 以从 firebase 获取一些数据以填充平面列表
useEffect(() => {
return db
.collection('accounts')
.doc(currentAccountId)
.collection('shops')
.doc(currentShopId)
.collection('sensors')
.onSnapshot((querySnapshot) => {
const list = [];
querySnapshot.forEach((doc) => {
const { sensorReadingsId } = doc.data();
// This works, but doesn't load the additional data I need.
// list.push({ ...{ id: doc.id }, ...doc.data() });
// This doesn't seem to load anything.
db.collection('sensors')
.doc(sensorReadingsId.toString())
.onSnapshot((documentSnapshot) => {
list.push({ ...{ id: doc.id }, ...doc.data(), ...documentSnapshot.data() });
});
});
setSensorsData(list);
console.log(sensorsData);
setLoading(false);
});
}, [currentAccountId, currentShopId]);
问题是:我的平面列表没有加载任何内容。当我最初加载屏幕时,console.log 输出一个空数组。如果我通过保存屏幕文件强制它重新渲染,则数组已正确填充。
如评论中所述,如果我只使用list.push({ ...{ id: doc.id }, ...doc.data() }); 而不是db.collection('sensors')...,它会很好地加载传感器,但没有我需要的额外数据。
我该如何解决这个问题?提前致谢!
解决方案:正如@Rajitha Udayanga 所指出的,根据列表数组检查第一个查询快照的长度是检查是否所有数据都已加载的好方法。这是工作代码(注意setSensorsData 已被移入的条件):
useEffect(() => {
return db
.collection('accounts')
.doc(currentAccountId)
.collection('shops')
.doc(currentShopId)
.collection('sensors')
.onSnapshot((querySnapshot) => {
const list = [];
querySnapshot.forEach((doc) => {
const { sensorReadingsId } = doc.data();
db.collection('sensors')
.doc(sensorReadingsId.toString())
.onSnapshot((documentSnapshot) => {
list.push({ ...{ id: doc.id }, ...doc.data(), ...documentSnapshot.data() });
// Fix is here:
if (querySnapshot.docs.length === list.length) {
setSensorsData(list);
console.log(sensorsData);
setLoading(false);
}
});
});
});
}, [currentAccountId, currentShopId]);
【问题讨论】:
标签: reactjs firebase react-native google-cloud-firestore react-hooks