firestore onSnapshot执行两次

use*_*914 3 firebase angular google-cloud-firestore

我的firestore onSnapshot()函数被调用了两次。

let user = firebase.firestore().collection('users').doc(userID).onSnapshot
({                    
    next: (documentSnapshot: firebase.firestore.DocumentSnapshot) =>
    {
         this.userArray.push(documentSnapshot as User);
         console.log(documentSnapshot);
         //here
    },
    error: (firestoreError: firebase.firestore.FirestoreError) =>
    {
         console.log(firestoreError);
         //here
    }
});
Run Code Online (Sandbox Code Playgroud)

我也尝试过在https://firebase.google.com/docs/firestore/query-data/listen#detach_a_listener中进行订阅,方法是在// here注释中包含user(),但无济于事。

我该如何修改,以使该函数仅执行一次,即每次仅推送一个用户对象,而不是两次。

gro*_*hjy 7

我不知道这是否与您的问题有关。如果正在使用

firebase.firestore.FieldValue.serverTimestamp()
Run Code Online (Sandbox Code Playgroud)

给文档加上时间戳,onSnaphot将触发两次。这似乎是因为将新文档添加到数据库时,onSnapshot将触发,但serverTimestamp尚未运行。几毫秒后,serverTimestamp将运行并更新您的文档=> onSnapshot将再次触发。

我想在onSnapshot触发之前添加一个小的延迟(例如0,5s左右),但是我找不到执行此操作的方法。

您还可以为onCreate事件创建一个服务器端功能,相信可以解决您的问题。也许您的userArray.push-action更适合在服务器端执行。


Dav*_*ast 1

如果您需要一次性响应,请使用 .get() 方法作为承诺。

firebase.firestore().collection('users').doc(userID).get().then(snap => {
  this.userArray = [...this.userArray, snap.doc);
});
Run Code Online (Sandbox Code Playgroud)

不过,我建议使用AngularFire(完全有偏见,因为我维护这个库)。它使处理常见的 Angular + Firebase 任务变得更加容易。

  • 这不是违背了使用`onSnapshot`的目的吗?据我了解,“get()”不会监听更改。 (7认同)