Node.js 使用MongoDB/Mongoose.js按月对标签进行分组

Node.js 使用MongoDB/Mongoose.js按月对标签进行分组,node.js,mongodb,mongoose,aggregation-framework,Node.js,Mongodb,Mongoose,Aggregation Framework,我在mongodb中的收藏如下所示: 帖子: // ... tags: [ { id: { type: mongoose.Schema.Types.ObjectId, ref: 'Tag', required: true, } // ... } ], date: { type: D

我在mongodb中的收藏如下所示:

帖子:

// ...
 tags: [
        {
            id: {
                type: mongoose.Schema.Types.ObjectId,
                ref: 'Tag',
                required: true,
            }
            // ... 
        }
 ],

 date: {
    type: Date,
 }
// ...
我想写一个查询,结果如下:

[
    {
      "month": "Jan",
      "tag1": 5,
      "tag2": 80,
      // ...
     }, 
    {
      "month": "Feb",
      "tag1": 30,
      "tag2": 95,
      // ...
    },
    // ...
]
我想我需要使用聚合。是这样吗

我写了这篇文章,但结果不是我想要的

  const monthStrings = ["", "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];
  Posst.aggregate([
    {
      $match: {
        $expr: {
          $and: [
            { $gt: ["$created_at", oneYearFromNow] },
            { $lt: ["$created_at", dateNow] }
          ],
        }
      }
    },
    {
      $group: {
        _id: {
          month: { $month: "$date" },
          year: { $year: "$date" },
        },
        count: {
          $sum: 1
        }
      }
    },
    {
      $project: {
        _id: {
          $concat: [
            {
              $arrayElemAt: [
                monthStrings,
                "$_id.month"
              ]
            },
            "-",
            "$_id.year"
          ]
        },
        count: 1,
      }
    }
  ])
我怎样才能得到我想要的结果


(返回的格式并不重要,但我尝试在单个查询中检索相同分组的计数(每月一个)。

为了统计每个标记的文档,您需要根据标记标识符进行分组。由于标记位于一个数组中,最简单的方法是在分组之前首先展开数组。最后,为了在单个文档中获取同一个月的所有标记,您需要执行第二个组操作。例如(假设要使用的标记的名称位于“ref”字段中):


你试过什么?添加另一个架构并为集合添加示例文档,并从该文档中添加预期结果。请检查我的编辑@如果您添加一些示例文档,turivishalit将有所帮助。可能类似于下面的答案,如果这有帮助的话。非常感谢。
Posst.aggregate([
  {
    $match: ... 
  },
  {
    // Unwind the tags array, produces one document for each element in the array
    $unwind: '$tags'
  },
  {
    // Group by month, year and tag reference
    $group: {
      _id: {
        month: { $month: '$date' },
        year: { $year: '$date' },
        tag: '$tag.ref'
      },
      count: { $sum: 1 }
    }
  },
  {
    // Group again by month and year to aggregate all tags in one document
    $group: {
      _id: {
        month: '$_id.month',
        year: '$_id.year'
      },
      // Collect tag counts into an array
      tagCounts: {
        $push: {
          k: '$_id.tag',
          v: '$count'
        }
      }
    }
  },
  {
    // Reshape document to have each tag in a separate field
    $replaceRoot: {
      newRoot: {
        $mergeObjects: [ 
          { month: '$_id.month', year: '$_id.year' },
          { $arrayToObject: '$tagCounts' }
        ]
      }
    }
  }
])