我正在尝试使用MongoDB的聚合框架从具有以下结构的集合生成文档:
{
"_id" : ObjectId("5510eb56f877bbef153d236d"),
"attributes" : {
"brand" : "Mercedes",
"price" : 289,
"family" : "GARDEN"
},
"name" : "Bigger Fix Soft Crisps"
}
{
"_id" : ObjectId("5510eb56f877bbef153d236e"),
"attributes" : {
"brand" : "Adelholzener",
"price" : 683,
"family" : "COMPUTER"
},
"name" : "Soft Stockhome Chips"
}
{
"_id" : ObjectId("5510eb56f877bbef153d236f"),
"attributes" : {
"brand" : "Pepsi",
"price" : 789,
"family" : "CAR"
},
"name" : "Light Yearsailfresh Meat"
}
我想从attributes
子文档中获取所有字段的聚合及其可能的值。由于子文档中的字段未知,因此我不能简单地使用此示例中给出的字段,因此必须是动态的。结果看起来应该类似于:
{
"_id" : "brand",
"values" : [
"Mercedes", "Adelholzener", "Pepsi"
]
},
{
"_id" : "price",
"values" : [
289, 683, 789
]
},
{
"_id" : "family",
"values" : [
"GARDEN", "COMPUTER", "CAR"
]
}
到目前为止,我还没有找到解决这个特殊问题的方法。我尝试使用$project
和$unwind
(显然这只适用于数组)。
答案 0 :(得分:1)
试图找出如何做到聚合,但我不确定它是否可能,因为你无法以任何好的方式获取对象中的键。
这是一个执行该操作的MapReduce作业:
db.runCommand({
"mapreduce" : "test_collection", // Change collection here
"map" : function() {
for (var key in this.attributes) {
// Emit objects w array as we cannot reduce arrays directly
emit(key, {x: [this.attributes[key]]});
}
},
"reduce" : function(key, values) {
var res = [];
values.forEach(function (d) {
Array.prototype.push.apply(res, d.x);
});
return {x: res};
},
"finalize": function (key, reducedVal) {
return reducedVal.x;
},
"out": { inline: 1 }
});