MongoDB/Mongoose orderby日期和groupby用户

MongoDB/Mongoose orderby日期和groupby用户,mongodb,mongoose,Mongodb,Mongoose,我有一个集合,其中多个文档可能具有相同的userId字段。我想按userId分组,这样我可以得到唯一的userIds列表,还可以按date排序,这样每个返回的文档都是该userId的最新文档。我用sql做过类似的查询,我真的希望它能用mongo实现 在此示例集合中: { userId: 456, date: 5/16/1988 }, { userId: 456, date: 5/17/1988 }, { userId: 789, date: 5/18/1988 }, { userId: 789,

我有一个集合,其中多个文档可能具有相同的
userId
字段。我想按
userId
分组,这样我可以得到唯一的
userId
s列表,还可以按
date
排序,这样每个返回的文档都是该
userId
的最新文档。我用sql做过类似的查询,我真的希望它能用mongo实现

在此示例集合中:

{ userId: 456, date: 5/16/1988 },
{ userId: 456, date: 5/17/1988 },
{ userId: 789, date: 5/18/1988 },
{ userId: 789, date: 5/17/1988 }
我想返回:

{ userId: 456, date: 5/17/1988 },
{ userId: 789, date: 5/18/1988 }

以下是您在mongo的操作方法。请注意,它使用的是yyyy-mm-dd的日期格式

db.collection.aggregate({
  $group: {
    id : '$userId',
    date: { $max: '$date'} 
  }
})

来源:

在你的问题中,你说你想退回完整的文件。您可以通过在
$group
操作符中将完整文档作为字段返回来完成此操作

db.coll.aggregate([
  {$sort:{date:-1}},
  {$group: {_id: "$userId", doc:{$first: "$$CURRENT"}} }
])
我创建了四个文档,如您的问题中所述,类型为一些随机日期。这将为您提供以下结果:

{
    "_id" : 789,
    "doc" : {
        "_id" : ObjectId("53d80e246ebc37d0c33321ba"),
        "userId" : 789,
        "date" : ISODate("2014-07-05T04:00:00.000Z")
    }
}, 
{
    "_id" : 456,
    "doc" : {
        "_id" : ObjectId("53d80e246ebc37d0c33321b8"),
        "userId" : 456,
        "date" : ISODate("2014-07-05T04:00:00.000Z")
    }
}

有关
$$CURENT

的更多信息,请参阅。尽管它们可能是正确的方法,但我无法使用db.collection.aggregate方法,因为我需要在模型上使用.populate()等其他方法。在这种情况下,请查找。因此,我提出了一个解决方案,在查找(选项)中对用户ID和日期进行排序,如下所示:

{ sort: { updateDate: -1, userId: -1 } }
然后,我在前端编写了一个函数来提取每个用户的最新记录:

filterLatest: function(docs) {
    var lastUserId = null;
    var latestDocs = [];

    docs.forEach(function(doc) {
        if(lastUserId != doc.userId) latestDocs.push(doc);
        lastUserId = doc.userId;
    });

    return latestDocs;
}

日期字段的数据类型到底是什么?我真的希望它不是一个以这种方式格式化的字符串,因为那将不可能排序。YYYYMMDD格式的字符串可以排序,因为字母排序可以工作。表示历元的数值(自固定时间点以来经过的秒数/分钟数/天数/任何值)会更好。但理想的解决方案是理想的BSON日期类型,因为你可以用它做更多的事情,而不仅仅是正确排序。有没有办法将它添加到mongoose find查询的选项字段中?希望它看起来像这样:
Model.find({},“,{$group:{id:$userId”,Date:{$max:$Date}})
。但它似乎不是这样工作的。@RobbyAllsopp在@RobbyAllsopp上签出Mongoose文档。如果您不使用Model.find(),您必须使用Model.aggregate(),那么这可能会起作用,但实际上我无法使用它,因为我要使用它的既定模式是Model.find()。不过还是要谢谢你。加,我希望这能起作用,但猫鼬不喜欢$$CURRENT。当我运行此查询时,我得到了这样的结果:
“异常:字段路径字段名不能以“$”开头。”