在Firebase中,如何查询最近的10个子节点?

我使用childByAutoId来生成我的孩子。 每个孩子看起来像这样:

{ user_id: 1 } 

我想得到最近添加的最后10个,按时间降序sorting。 什么是最简单的方法来做到这一点?

答案是,您需要使用一些反向逻辑,并在每个节点中存储一个时间戳记:值对作为负值。 我省略了user_id:1来保持答案的清晰。

这里是Firebase结构

 "test" : { "-KFUR91fso4dEKnm3RIF" : { "timestamp" : -1.46081635550362E12 }, "-KFUR9YH5QSCTRWEzZLr" : { "timestamp" : -1.460816357590991E12 }, "-KFURA4H60DbQ1MbrFC1" : { "timestamp" : -1.460816359767055E12 }, "-KFURAh15i-sWD47RFka" : { "timestamp" : -1.460816362311195E12 }, "-KFURBHuE7Z5ZvkY9mlS" : { "timestamp" : -1.460816364735218E12 } } 

这是如何写入Firebase的; 我只是用一个IBActionbutton来写出几个节点:

 let testRef = self.myRootRef.childByAppendingPath("test") let keyRef = testRef.childByAutoId() let nodeRef = keyRef.childByAppendingPath("timestamp") let t1 = Timestamp nodeRef.setValue( 0 - t1) //note the negative value 

和读取它的代码

  let ref = self.myRootRef.childByAppendingPath("test") ref.queryOrderedByChild("timestamp").queryLimitedToFirst(3).observeEventType(.ChildAdded, withBlock: { snapshot in print("The key: \(snapshot.key)") //the key }) 

我宣布了一个小函数来返回当前的时间戳

 var Timestamp: NSTimeInterval { return NSDate().timeIntervalSince1970 * 1000 } 

和输出

 The key: -KFURBHuE7Z5ZvkY9mlS The key: -KFURAh15i-sWD47RFka The key: -KFURA4H60DbQ1MbrFC1 

正如你所看到的,它们是相反的。

注意事项:

  1. 写出你的时间戳为负值
  2. 在阅读中使用.queryLimitedToFirst而不是最后。

在这个笔记上,你也可以像往常一样读取数据,并将其添加到一个数组,然后对数组进行降序sorting。 这会使客户端付出更多的努力,如果有10,000个节点可能不是一个好的解决scheme。

我假设你的数据看起来像这样:

 someDataSet: { longUID-1: { timeCreated: 9999999999, // (seconds since the javascript epoch) user_id: 1 }, longUID-2: { timeCreated: 1111111111, user_id: 2 }, longUID-3: { timeCreated: 3141592653, user_id: 3 } } 

您可以通过在for循环或任何其他方法中多次调用Firebase.push({user_id: ###, timeCreated: ###})来自动执行该操作。 也许你正在向网页添加新闻故事,但你只希望你的用户看到最新的故事— IDK。 但是,您的问题的答案是使用Firebase的ref.orderByChild()ref.limitToLast()

 var ref = new Firebase("<YOUR-FIREBASE-URL>.firebaseio.com/someDataSet"); //the "/someDataSet" comes from the arbitrary name that I used up above var sortedRef = ref.orderByChild('timeCreated'); //sort them by timeCreated, ascending sortedRef.limitToLast(2).on("child_added", function(snapshot){ var data = snapshot.val(); console.log(data); /* do something else with the data */ }); //The console would look like this // Object {timeCreated: 9999999999, user_id: 1} // Object {timeCreated: 3141592653, user_id: 3} 

发生这种情况的原因是程序以最大的时间timeCreated了孩子,然后是第二个最大的(值)秒……还要注意,longUID在按孩子sorting时没有任何意义,而其他值(user_id在这种情况下)

这里是文档:

  • Firebase .push()方法(对不起,我不允许发布此链接 – 我没有足够的声誉)
  • Firebase .orderByChild方法
  • 还有, Firebase .limitToLast方法

代码: ref.queryOrderedByKey().queryLimitedToLast(10)可用于获取最近的10个数据。 但是,这是默认情况下的升序。

或者,您可以通过订购您的数据

 ref.orderByChild("id").on("child_added", function(snapshot) { console.log(snapshot.key()); }); 

这也是默认情况下的升序。 把它改成降序是有点棘手的。 我会build议它乘以-1,如下所示,然后sorting它们。

 var ref= new Firebase("your data"); ref.once("value", function(allDataSnapshot) { allDataSnapshot.forEach(function(dataSnapshot) { var updatedkey = -1 * dataSnapshot.key(); ref.update({ element: { id: updatedkey}}); }); }); 

这两个SO页面也许对你有用,请检查:

如何删除Firebase节点中除最新的X个子项外的所有项目?

firebaseArray降序?