聚合:我将如何计算值为真的键的数量?

Aggregation: How would I count the number of keys for which the value is true?

我在 mongodb 中有大量文档,它们看起来像这样:

[
  {
    name: "steve",
    accountFeatures: {word: true, excel: false, powerpoint: true}
  },
  {
    name: "john",
    accountFeatures: {word: false, excel: true, powerpoint: true, notes: true}
  },
  {
    name: "rick",
    accountFeatures: {word: true, excel: false, powerpoint: true}
  }
]

我想运行一个聚合来找出对象中的每个键有多少被设置为真(实际数据中有更多的键),所以预期的输出示例数据为:

  {
    "res": {
      "excel": 1,
      "notes": 1,
      "powerpoint": 3,
      "word": 2
    }
  }

这可能吗?到目前为止,我能想到的就是:

[
  {
    '$project': {
      '_id': 0, 
      'accountFeatures': 1
  }
]

您可以使用 $objectToArray$unwind 这将允许我们 $group 按键:

db.collection.aggregate([
  {
    $set: {accountFeatures: {$objectToArray: "$accountFeatures"}}
  },
  {
    $project: {
      accountFeatures: {
        $filter: {
          input: "$accountFeatures",
          as: "item",
          cond: {$eq: ["$$item.v", true]}
        }
      }
    }
  },
  {
    $unwind: "$accountFeatures"
  },
  {
    $group: {_id: "$accountFeatures.k", v: {$sum: 1}}
  },
  {
    $group: {_id: 0, data: {$push: {k: "$_id", v: "$v"}}}
  },
  {
    $project: {res: {$arrayToObject: "$data"}, _id: 0}
  }
])
  1. $objectToArray 提取密钥
  2. $filter 只保留 true
  3. $unwind 将不同文档的键分开
  4. $group对每个键进行计数
  5. 格式化结果 Playground example