ReactJS 从Firebase查询数据排序异常 新增数据无法追加到数组末尾
问题解决方法
问题原因
Firestore 默认没有按数据提交时间排序的规则,调用add()方法新增数据时返回的文档顺序默认按随机生成的文档ID升序排列,所以新提交的数据不会自动追加到数组末尾。
修改步骤
1. 调整数据提交逻辑,新增排序用时间字段
当前代码中存储的date_time是本地化可读字符串,无法用于时间排序,新增create_time字段存储Firebase服务端时间戳,避免客户端时间不准导致的排序异常:
const dataInput = { date_time: new Date().toLocaleString(), create_time: firebase.firestore.FieldValue.serverTimestamp(), // 新增服务端时间戳字段用于排序 message, sender_id: userId, }; db.collection("messages").add(dataInput);
若使用Firebase v9及以上模块化SDK,将
firebase.firestore.FieldValue.serverTimestamp()替换为从firebase/firestore引入的serverTimestamp()即可。
2. 调整查询逻辑,指定排序规则
查询时指定按create_time升序排列,即可实现旧数据在前、新提交数据追加在末尾的效果:
db.collection("messages") .orderBy("create_time", "asc") .onSnapshot((snap) => { let messages = []; snap.docs.forEach((doc) => { messages.push({ ...doc.data(), id: doc.id }); }); console.log(messages); setmessge(messages); });
补充说明
首次运行带orderBy的查询时,Firebase控制台会弹出索引创建提示,按提示完成索引创建并等待生效后,查询即可正常返回预期顺序的结果。
如果不想新增字段,也可以直接用文档元数据的创建时间做前端排序,性能略低于查询端排序,写法参考:
snap.docs.sort((a,b) => a.createTime.toMillis() - b.createTime.toMillis())
内容的提问来源于stack exchange,提问作者Muddusar Zulfiqar
相关产品推荐
相关产品推荐

