【发布时间】:2021-06-07 17:55:53
【问题描述】:
我遇到了 Firestore 问题,希望有人能帮我解决。
我有一个似乎正在破坏排序行为的活动文档快照侦听器,我不知道为什么。
在我的组件的构造函数中,我初始化了一次文档快照监听器:
this.listen = this.fs.collection('users').doc('0EwcWqMVp9j0PtNXFDyO').ref.onSnapshot(t => {
console.log(t)
})
每当我单击“排序”按钮时,它都会初始化一个按名字排序的新集合查询。
async onSort() {
if (this.first) {
this.first();
}
this.sort = this.sort === 'asc'? 'desc' : 'asc';
alert(this.sort)
let arr = []
let lastDoc = null
let queryRef = this.fs.firestore.collection('users').orderBy('firstName', this.sort as any).limit(20);
this.users$ = this._users$.asObservable()
// initialize a blank list
this._users$.next([])
// subscribe to user list snapshot changes
const users1: { users: any, last: any } = await new Promise((resolve, reject) => {
this.first = queryRef.onSnapshot((doc) => {
console.log("Current data: ", doc);
const users = doc.docs.map(t => {
return {
id: t.id,
...t.data() as any
}
})
console.log(users)
resolve({
users: users,
last: doc.docs[doc.docs.length -1]
})
});
})
this._users$.next(this._users$.value.concat(users1.users))
}
但是,这并没有按预期工作。排序返回一条记录(应该有 20 条记录,基于限制)。
有趣的是,取消订阅文档快照会修复排序问题。正在返回 20 条记录,并且排序行为正确。
谁能解释一下我做错了什么?
这是重现该问题的最小 Stackblitz。
[编辑]
越来越接近解决方案和理解...... 感谢@ZackReam 的解释以及@Robin 和@Zack 的规范答案。
似乎this._firestore.firestore.collection('users').orderBy('firstName', this.sort as any).limit(20).onSnapshot(...) 确实发出了两次 - 一次用于活动文档侦听器(缓存中有 1 条记录),第二次用于排序集合(因为switchMap 将不在缓存中每次执行 sort 时取消订阅)。
我们可以在 Zack 发布的功能演示中简单地看到 - 它闪烁着与文档侦听器相对应的一条记录,然后片刻之后,列表中填充了排序后的集合。
您的听众越活跃,结果的闪现就越奇怪。这是设计使然吗?对我来说似乎有缺陷...
直观地说,我希望 this._firestore.firestore.collection('users').orderBy('firstName', this.sort as any).limit(20) 查询中的 snapshotChanges() 或 valueChanges() 返回 20 个结果(排序后的前 20 个),独立于任何其他文档侦听器。来自该查询的第一个快照是来自文档查询的初始活动文档,这是违反直觉的 - 这应该与排序查询无关。
【问题讨论】:
标签: angular google-cloud-firestore angularfire angularfire5