Mongodb排序内部数组

Mongodb排序内部数组,mongodb,aggregation-framework,Mongodb,Aggregation Framework,我已经找了一段时间了,似乎无法对内部数组进行排序并将其保存在我当前正在处理的文档中 { “服务”:{ “应用程序”:{ “更新”:[ { “n”:1 “日期”:ISODate(“2012-03-10T16:15:00Z”) }, { “n”:2 “日期”:ISODate(“2012-01-10T16:15:00Z”) }, { “n”:5 “日期”:ISODate(“2012-07-10T16:15:00Z”) } ] } } } 因此,我希望保留要作为服务返回的项目,但对更新数组进行排序。到

我已经找了一段时间了,似乎无法对内部数组进行排序并将其保存在我当前正在处理的文档中

{
“服务”:{
“应用程序”:{
“更新”:[
{
“n”:1
“日期”:ISODate(“2012-03-10T16:15:00Z”)
},
{
“n”:2
“日期”:ISODate(“2012-01-10T16:15:00Z”)
},
{
“n”:5
“日期”:ISODate(“2012-07-10T16:15:00Z”)
}
]
}
}
}
因此,我希望保留要作为服务返回的项目,但对更新数组进行排序。到目前为止,我对壳牌公司有:

db.servers.aggregate(
{$unwind:'$service'},
{$project:{'service.apps':1}},
{$unwind:'$service.apps'},
{$project:{'service.apps.updates':1}},
{$sort:{'service.apps.updates.date':1}});

有人认为他们可以在这方面提供帮助吗?

你可以通过
$unwind
调用
updates
数组,按
日期对生成的文档进行排序,然后
$group
使用排序顺序将它们重新组合在一起

db.servers.aggregate(
{$unwind:'$service.apps.updates'},
{$sort:{'service.apps.updates.date':1},
{$group:{{{u id:'${u id','updates':{$push:'$service.apps.updates'}},
{$project:{'service.apps.updates':'$updates'})

您可以通过
$unwind
使用
updates
数组,按
日期对生成的文档进行排序,然后使用排序顺序将它们重新组合在一起

db.servers.aggregate(
{$unwind:'$service.apps.updates'},
{$sort:{'service.apps.updates.date':1},
{$group:{{{u id:'${u id','updates':{$push:'$service.apps.updates'}},
{$project:{'service.apps.updates':'$updates'})

Mongo4.4
开始,聚合操作符允许应用自定义javascript函数来实现MongoDB查询语言不支持的行为

例如,要按对象的一个字段对对象数组进行排序,请执行以下操作:

// {
//   "service" : { "apps" : { "updates" : [
//     { "n" : 1, "date" : ISODate("2012-03-10T16:15:00Z") },
//     { "n" : 2, "date" : ISODate("2012-01-10T16:15:00Z") },
//     { "n" : 5, "date" : ISODate("2012-07-10T16:15:00Z") }
//   ]}}
// }
db.collection.aggregate(
  { $set: {
    { "service.apps.updates":
      { $function: {
          body: function(updates) {
            updates.sort((a, b) => a.date - b.date);
            return updates;
          },
          args: ["$service.apps.updates"],
          lang: "js"
      }}
    }
  }
)
// {
//   "service" : { "apps" : { "updates" : [
//     { "n" : 2, "date" : ISODate("2012-01-10T16:15:00Z") },
//     { "n" : 1, "date" : ISODate("2012-03-10T16:15:00Z") },
//     { "n" : 5, "date" : ISODate("2012-07-10T16:15:00Z") }
//   ]}}
// }

这将在适当的位置修改阵列,而不必应用昂贵的
$unwind
$sort
$group
阶段的组合

$function
采用3个参数:

  • body
    ,它是要应用的函数,其参数是要修改的数组
  • args
    ,其中包含
    函数体作为参数的记录字段。在我们的例子中,
    “$service.apps.updates”
  • lang
    ,这是编写
    函数体的语言。目前只有
    js
    可用

Mongo4.4
开始,聚合操作符允许应用自定义javascript函数来实现MongoDB查询语言不支持的行为

例如,要按对象的一个字段对对象数组进行排序,请执行以下操作:

// {
//   "service" : { "apps" : { "updates" : [
//     { "n" : 1, "date" : ISODate("2012-03-10T16:15:00Z") },
//     { "n" : 2, "date" : ISODate("2012-01-10T16:15:00Z") },
//     { "n" : 5, "date" : ISODate("2012-07-10T16:15:00Z") }
//   ]}}
// }
db.collection.aggregate(
  { $set: {
    { "service.apps.updates":
      { $function: {
          body: function(updates) {
            updates.sort((a, b) => a.date - b.date);
            return updates;
          },
          args: ["$service.apps.updates"],
          lang: "js"
      }}
    }
  }
)
// {
//   "service" : { "apps" : { "updates" : [
//     { "n" : 2, "date" : ISODate("2012-01-10T16:15:00Z") },
//     { "n" : 1, "date" : ISODate("2012-03-10T16:15:00Z") },
//     { "n" : 5, "date" : ISODate("2012-07-10T16:15:00Z") }
//   ]}}
// }

这将在适当的位置修改阵列,而不必应用昂贵的
$unwind
$sort
$group
阶段的组合

$function
采用3个参数:

  • body
    ,它是要应用的函数,其参数是要修改的数组
  • args
    ,其中包含
    函数体作为参数的记录字段。在我们的例子中,
    “$service.apps.updates”
  • lang
    ,这是编写
    函数体的语言。目前只有
    js
    可用

太棒了!我对聚合非常陌生,有一种感觉它可以做这样的事情。如果应用程序有一个像“name”这样的字段,我想把这个名称也保留在结果集中呢?@user1251624您可以将该字段包括在
$group
(在
\u id
中或作为一个单独的字段)和
$project
中。如果你在这方面需要更多的帮助,最好把它作为一个独立的问题来问,因为这可能不是一个琐碎的问题。@johnyhk是
ing在
排序之后的顺序
总是有保证的吗?@RaR For
$push
是的,谢谢。不幸的是,
$addToSet
没有。太棒了!我对聚合非常陌生,有一种感觉它可以做这样的事情。如果应用程序有一个像“name”这样的字段,我想把这个名称也保留在结果集中呢?@user1251624您可以将该字段包括在
$group
(在
\u id
中或作为一个单独的字段)和
$project
中。如果你在这方面需要更多的帮助,最好把它作为一个独立的问题来问,因为这可能不是一个琐碎的问题。@johnyhk是
ing在
排序之后的顺序
总是有保证的吗?@RaR For
$push
是的,谢谢。不幸的是,对于
$addToSet
否。对于Atlas用户,
$function
在免费层不可用(截至2021年5月),对于Atlas用户,
$function
在免费层不可用(截至2021年5月)