无法从MongoDB返回最新文档

时间:2015-01-25 05:57:18

标签: mongodb mlab

我是MongoDB的新手,但我似乎对Herola使用的Mongolab有一个小问题。

如果我插入新文档,我不会收到任何错误。但Mongolab的MongoDB似乎在某个文档之后没有返回任何文档。也不是我插入的最新文档。

这是一个例子;我插入一个新文档并查询最新文档。它应该是一样的,对吧。但事实并非如此。

rs-ds027491:PRIMARY> db.measurements.insert({"temperature":"24.687","timestamp":"Sat, 24 Jan 2015 16:00:02 -0000","epoch_timestamp":1422108002})

WriteResult({ "nInserted" : 1 })

rs-ds027491:PRIMARY> db.measurements.find().limit(1).sort({$natural:-1})

{ "_id" : ObjectId("54c37fe687db950c001d04f4"), "temperature" : "24.75", "timestamp" : "Sat, 24 Jan 2015 13:20:02 -0000", "epoch_timestamp" : 1422098402 }

我也尝试迭代所有文档(从命令行和使用Robomongo。我在两者中得到相同的结果):

db.measurements.find({})
... after some 'it's...
{ "_id" : ObjectId("54c37eba87db950c001d04f3"), "temperature" : "24.75", "timestamp" : "Sat, 24 Jan 2015 13:15:02 -0000", "epoch_timestamp" : 1422098102 }
{ "_id" : ObjectId("54c37fe687db950c001d04f4"), "temperature" : "24.75", "timestamp" : "Sat, 24 Jan 2015 13:20:02 -0000", "epoch_timestamp" : 1422098402 }

正如您所看到的,最后一个文档也是上面的查询返回的文档,而不是我插入的最新文档。

Mongo或Mongolab有什么我不明白的东西,或者这应该有用吗 - 但它不是出于某种原因吗?

2 个答案:

答案 0 :(得分:2)

虽然在新的小集合中看起来似乎不同,但自然顺序与插入顺序不同。自然顺序按照集合的内部数据结构的顺序返回文档,这些数据结构针对性能进行了优化,而不是跟踪插入时间。

http://docs.mongodb.org/manual/reference/operator/meta/natural/

如果您希望在与每个文档相关的某些事件(例如插入时间,上次更新时间)之前对文档进行排序,我建议将该时间明确地作为字段进行跟踪,将该字段编入索引,然后在查询中按它排序。

答案 1 :(得分:1)

您永远不应该依赖自然顺序来为您提供一致的排序。

我会在此引用docs

  

通常,自然顺序反映了插入顺序,除非是   由于更新或删除文档增长导致文档重定位   操作释放空间,然后由新插入的空间占用   文档。

通过_id排序文档可以预期更一致的行为(请阅读Adam's answer)。但是,即使是this can fail

  

ObjectId值的顺序与生成之间的关系   时间在一秒钟内不严格。如果是多个系统,或者   单个系统上的多个进程或线程生成值,   在一秒钟内; ObjectId值不代表严格   插入顺序。客户端之间的时钟偏差也可能导致   因为客户端驱动程序生成,所以即使是值也不严格排序   ObjectId值,而不是mongod进程。

为此目的创建特定字段(如日期)并将其编入索引可能是最好和最简单的方法。