首页 > 解决方案 > MongoDB - 按方面结果分组

问题描述

如果我有以下收藏

顾客

[
    {
      uuid: "first",
      culture: "it-it"
    },
    {
      uuid: "second",
      culture: "de-de"
    }
]

车辆

[
    {
      model: "mymodel",
      users: [
        {
          uuid: "first",
          isOwner: true,
          createdOn: "2019-05-15T06: 00: 00"
        }
      ]
    },
    {
      model: "mymodel",
      users: [
        {
          uuid: "first",
          isOwner: false,
          createdOn: "2019-05-15T06: 00: 00"
        },
        {
          uuid: "second",
          isOwner: true,
          createdOn: "2019-05-15T06: 00: 00"
        }
      ]
    }
]

以及以下查询:

db.customers.aggregate([
  {
    $lookup: {
      from: "vehicles",
      let: {
        uuid: "$uuid"
      },
      pipeline: [
        {
          $match: {
            $expr: {
              $in: [
                "$$uuid",
                "$users.uuid"
              ]
            }
          }
        },
        {
          $project: {
            model: 1,
            users: {
              $filter: {
                input: "$users",
                as: "user",
                cond: {
                  $eq: [
                    "$$user.uuid",
                    "$$uuid"
                  ]
                }
              }
            }
          }
        },
        {
          $unwind: "$users"
        },
        {
          $replaceRoot: {
            newRoot: {
              isOwner: "$users.isOwner",
              createdOn: "$users.createdOn"
            }
          }
        }
      ],
      as: "vehicles"
    }
  },
  {
    $facet: {
      "createdOn": [
        {
          $match: {
            "vehicles": {
              $elemMatch: {
                isOwner: true,
                $and: [
                  {
                    "createdOn": {
                      $gte: "2019-05-15T00: 00: 00"
                    }
                  },
                  {
                    "createdOn": {
                      $lt: "2019-05-16T00: 00: 00"
                    }
                  }
                ]
              }
            }
          }
        },
        {
          $project: {
            culture: 1,
            count: {
              $size: "$vehicles"
            }
          }
        },
        {
          $group: {
            _id: 0,
            "total": {
              $sum: "$count"
            }
          }
        }
      ]
    }
  },
  {
    $project: {
      "CreatedOn": {
        $arrayElemAt: [
          "$CreatedOn.total",
          0
        ]
      }
    }
  }
])

我得到以下结果:

[
  {
    "createdOn": 2
  }
]

我想要达到的结果如下:

[
    {
        culture: "it-it",
        results: {
            "createdOn": 1
        }
    },
    {
        culture: "de-de",
        results: {
            "createdOn": 1
        }
    }
]

但我似乎无法弄清楚我可以在哪里分组以便我能得到那个结果。有人可以告诉我这样做的方法吗?

查询更复杂,指标更多,因此这是我所拥有的精简版本。

我尝试在任何地方进行分组,但未能得到我想要的结果。

标签: mongodbgroupingfacet

解决方案


以下查询可以为我们提供预期的输出:

db.customers.aggregate([
  {
    $lookup: {
      "from": "vehicles",
      "let": {
        "uuid": "$uuid"
      },
      "pipeline": [
        {
          $unwind: "$users"
        },
        {
          $match: {
            $expr: {
              $and: [
                {
                  $eq: ["$users.uuid", "$$uuid"]
                },
                {
                  $eq: ["$users.isOwner", true]
                },
                {
                  $gte: ["$users.createdOn", "2019-05-15T00: 00: 00"]
                },
                {
                  $lte: ["$users.createdOn", "2019-05-16T00: 00: 00"]
                }
              ]
            }
          }
        },
        {
          $count:"totalVehicles"
        }
      ],
      as: "vehiclesInfo"
    }
  },
  {
    $unwind: {
      "path": "$vehiclesInfo",
      "preserveNullAndEmptyArrays": true
    }
  },
  {
    $group: {
      "_id": "$culture",
      "culture": {
        $first: "$culture"
      },
      "createdOn": {
        $sum: "$vehiclesInfo.totalVehicles"
      }
    }
  },
  {
    $project: {
      "_id": 0,
      "culture": 1,
      "results.createdOn": "$createdOn"
    }
  }
]).pretty()

输出:

{ "culture" : "de-de", "results" : { "createdOn" : 1 } }
{ "culture" : "it-it", "results" : { "createdOn" : 1 } }

推荐阅读