我的Firebase聊天应用程序有问题。对于数据库部分,我正在使用Firestore Cloud。问题是每次我从数据库中删除一条消息时,消息侦听器都会触发两次:
这是我的快照侦听器代码:
chatListener = db.collection(ALL_CHAT)
.orderBy(SEND_TIME, Query.Direction.DESCENDING)
.limit(20)
.addSnapshotListener((messagesDocumentSnapshot, e) -> {
if (!messagesDocumentSnapshot.getDocumentChanges().isEmpty()) {
List<Message> messages = new ArrayList<>();
messagesDocumentSnapshot.getDocumentChanges().forEach(documentChange -> {
if (documentChange.getType() == DocumentChange.Type.ADDED) {
Message message = documentChange.getDocument().toObject(Message.class);
message.setId(documentChange.getDocument().getId());
messages.add(message);
}
});
if (!messages.isEmpty()) {
Collections.reverse(messages);
allChatFragment.updateMessages(messages, POSITION_END);
}
}
});
这是删除的代码:
db.collection(ALL_CHAT)
.document(id)
.delete();
答案 0 :(得分:1)
您的查询说“请给我SEND_TIME排序的前20个文档”:
chatListener = db.collection(ALL_CHAT)
.orderBy(SEND_TIME, Query.Direction.DESCENDING)
.limit(20)
将侦听器附加到侦听器时,排名前20位的任何文档随时间变化的时间将每次调用该侦听器。
从前20名中删除文档时,侦听器将收到一个回调,告诉您删除了哪个文档。并且,由于您的查询始终希望进入前20位,因此将再次调用侦听器,以告诉您另一个文档现在已进入前20位(以前位于第21位)。这将显示为“添加的”文档。
因此,您的听众正在按预期方式工作。您的听众应该准备随时处理对前20个文档的任何更改。
答案 1 :(得分:0)
这是预期的行为。
删除文档时,如果它是查询所匹配的文档之一,则将从查询结果中删除该文档,并通知每个侦听器该值已删除。
现在,您的查询只匹配它想要的20个文档中的19个文档,因此将向每个侦听器通知一个符合您查询选择标准的新文档。 “添加”文档时,并不意味着将文档添加/上传到数据库,而是将其添加到查询结果列表中。