Firebase child_added不首先加载所有数据

时间:2014-06-19 17:27:40

标签: javascript firebase

我有一个应用程序,其中我想加载一些初始数据(使用Firebase.once('value')完成)然后在某个时候我想要接收已添加到该Firebase的子节点的事件参考

为此,我想使用Firebase.on('child_added'),但根据定义(并在实践中看到),它首先加载Firebase参考的所有数据。

有没有办法绕过这种行为并只监听child_added个事件。此外,像转储初始数据集这样的解决方法不是解决方案(想象一下拥有超过一百万个数据点的数据集 - 我不希望每个数据点都只是为了在添加数据时进行监听!)。

编辑:Firebase.on('child_added')可以与limit()结合使用,以限制初始请求产生的数据量。可能对我的应用程序而言,在某个时间点只会向Firebase添加一个数据点,因此我使用了Firebase.limit(1).on('child_added')来限制加载到单个数据点的初始数据量。但是,我不喜欢这种解决方法有两个原因:

  1. 这仍然是一种解决方法。我仍然不得不忽略我不应该担心忽略的数据。
  2. 如果由于某种原因我的应用程序的性质发生了变化,而我一次要将多个子项添加到Firebase引用中 - 会强制limit(1)限制应用程序接收所有添加的子项?我不确定是否是这种情况,或者是否会为每个添加的孩子调用child_added,无论他们是否作为批次添加。
  3. 似乎提供一个true/false标志作为调用的参数将是一个很好的解决方案,但我会等待,看看是否有一个我一直在掩饰的答案......

1 个答案:

答案 0 :(得分:5)

删除旧邮件

如果您对历史数据不感兴趣,那么您将其用作消息队列。如果是这种情况,则应在阅读之后删除(或存档到备用路径)旧记录。这样,问题就是自我解决。

如果您想维护此型号,可以使用几个不错的选项:

存储最后一个读取密钥并将其用作下次加载的起点

您甚至可以将密钥存储在Firebase中

var fb = new Firebase(URL);
fb.child('last_read_key').once('value', function(lastReadSnap) {
   var lastKey = lastReadSnap.val();
   var pri = lastReadSnap.getPriority();
   fb.child('data_to_read').startAt(pri, lastKey).on('child_added', function(snap) {
      if( snap.name() !== lastKey ) {
         console.log('new record', snap.name());
         fb.child('last_read_key').setWithPriority(snap.name(), snap.getPriority());
      }
   });
});

使用优先级标记旧记录的时间戳

编写记录时,请使用setWithPriority:

fb.child('records/$recordid').setWithPriority(data, Firebase.ServerValue.TIMESTAMP);

现在您可以阅读从“now”开始的记录:

fb.child('records').startAt(Date.now()).on('child_added', function(snap) {
    console.log('new child', snap.name());
});

请注意这里使用时间戳的一个警告。我在startAt()命令中使用了Date.now(),因为它目前不支持Firebase.ServerValue.TIMESTAMP(为此提交的bug)。