问题描述
我正在为 firebase cloud firestore 获取集合中的所有文档。我正在使用 useEffect 钩子调用一个函数,该函数获取所有文档,然后使用一组新文档设置状态,但状态似乎没有更新。
const fetchBlogs = () => {
db.collection('blogs').get().then(querySnapshot => {
querySnapshot.forEach(doc => {
setBlogs([...blogs,{
title:doc.data().title,imgurL: doc.data().imgurL,desc: doc.data().desc
}])
});
});
}
useEffect(() => {
fetchBlogs();
},[]);
{
blogs && blogs.map(blog=>{
return(
<Article
key={blog.title}
title={blog.title}
imgurl = {blog.imgurL}
desc={blog.desc}
/>
)
})
}
解决方法
更新 state
中的 forEach
并不能保证状态更新。先生成数据,然后更新状态 state
。您可以阅读 these answer 以了解有关在循环内运行 setState
的更多信息
const fetchBlogs = () => { // You can also move this inside `useEffect` incase if it's not reused.
db.collection('blogs').get().then(querySnapshot => {
const querySnapshots = []
querySnapshot.forEach(doc => {
const { title,imgURL,desc } = doc.data()
querySnapshots.push({ title,desc })
});
setBlogs([...blogs,...querySnapshots])
});
}
useEffect(() => {
fetchBlogs();
},[]);
,
改变
querySnapshot.forEach(doc => {
setBlogs([...blogs,{
title: doc.data().title,imgURL: doc.data().imgURL,desc: doc.data().desc
}])
});
到
setBlogs(
querySnapshot.docs.map(doc => ({
title: doc.data().title,desc: doc.data().desc
}))
);
多次调用 setBlogs()
并从闭包中引用 blogs
将会失败。每次调用 blogs
时,旧闭包中对 setBlogs()
的引用不会更新,因此一系列状态更新只会呈现快照中迭代的最后一个文档,就像您当前编写它的方式一样。