【问题标题】:mongoose aggregate on a nested array嵌套数组上的猫鼬聚合
【发布时间】:2021-04-14 18:35:48
【问题描述】:

我有一个包含子数组的架构,并且它的每个元素都引用另一个架构,如下所示:

{
 _id: "5fed222d806311ec81d6df23"
 someOtherNestedDoc: {
    _id: "abc",
    someOtherField: 10
 },
 matches: [
   {
      _id: "5fed222d806311ec81d6daf3",
      user: "5fed222d806311ec81d6dcf3",
      probability: 10
   },
   {
      _id: "5fed222d806311ec81d6d1f3",
      user: "5fed222d806311ec81d62cf3",
      probability: 20
   },
 ]
}

我想做一个 Mongoose 聚合,在其中我查找每个匹配项的用户引用,并且只为它项目 3 个字段,2 个已经存在,第三个是该模式的数组的总和,所以最后,我有这样的事情:

{
 _id: "5fed222d806311ec81d6df23"
 someOtherNestedDoc: {
    _id: "abc",
    someOtherField: 10
 },
 matches: [
   {
      _id: "5fed222d806311ec81d6daf3",
      user: {
         firstName: "Max",
         lastName: "Mustermann",
         totalExpenses: 100
      },
      probability: 10
   },
   {
      _id: "5fed222d806311ec81d6d1f3",
      user: {
         firstName: "Herbert",
         lastName: "Mustermann",
         totalExpenses: 200
      },,
      probability: 20
   },
 ]
}

用户看起来像这样:

{
  _id: "5fed222d806311ec81d6dcf3",
  firstName: "Max",
  lastName: "Mustermann",
  password: "test",
  expenses: [
    {
      _id: 1,
     price: 50
    },
    {
      _id: 2,
     price: 50
    },
   ]
}

{
  _id: "5fed222d806311ec81d62cf3",
  firstName: "Herbert",
  lastName: "Mustermann",
  password: "test2",
  expenses: [ 
    {
      _id: 3,
     price: 75
    },
    {
      _id: 4,
     price: 125
    },
   ]
}

【问题讨论】:

    标签: javascript mongodb mongoose aggregate


    【解决方案1】:
    • $unwind解构matches数组
    • $lookup 带有用户集合并在 let 中传递用户 ID,
      • $matchuserId 条件
      • $project 显示必填字段,得到expenses.price 的总和
    • $unwind解构user数组
    • $group by _id 并重构 matches 数组
    db.col1.aggregate([
      { $unwind: "$matches" },
      {
        "$lookup": {
          "from": "user",
          let: { userId: "$matches.user" },
          pipeline: [
            { $match: { $expr: { $eq: ["$_id", "$$userId"] } } },
            {
              $project: {
                _id: 0,
                firstName: 1,
                lastName: 1,
                totalExpenses: { $sum: "$expenses.price" }
              }
            }
          ],
          "as": "matches.user"
        }
      },
      { $unwind: "$matches.user" },
      {
        $group: {
          _id: "$_id",
          matches: { $push: "$matches" }
        }
      }
    ])
    

    Playground

    【讨论】:

    • 这通常工作得很好,唯一的事情是,如果我在原始文档中除了“匹配”之外还有其他字段,那么这些字段就会丢失。我怎样才能保存这些?我编辑了问题。
    • 你可以使用带有字段名的 $first 运算符看看这个playground
    猜你喜欢
    • 2020-05-10
    • 2021-05-06
    • 2020-06-12
    • 2015-08-21
    • 2015-05-02
    • 2018-10-30
    • 2019-11-15
    • 2021-08-05
    • 2021-09-12
    相关资源
    最近更新 更多