解决此问题的一种方法是运行一个聚合管道,以获取有关文档根级别的键的数据,
由系统变量$$ROOT 表示,遍历它们的值并确定它们是否具有多个键。
第一步,使用$addFields添加一个包含上述计算的额外字段并使用$objectToArray进行转换
[ { k: 'key name': v: 'value' }, ... ]数组的键/值对
db.collection.aggregate([
{ '$addFields': {
'myKeys': { '$objectToArray': '$$ROOT' }
} }
])
获得这个数组后,下一步将是迭代列表并将值字段转换为数组。
然后通过比较数组的大小来过滤值是必要的,如果它有多个元素,那就是你的人
db.collection.aggregate([
{ '$addFields': {
'myKeys': {
'$map': {
'input': { '$objectToArray': '$$ROOT' },
'in': {
'k': '$$this.k',
'v': {
'$cond': [ // condition to convert the _id key value in ROOT to a single element array
{ '$eq': ['$$this.k', '_id'] },
['$$this.v'],
{ '$objectToArray': '$$this.v' } // convert the rest of the keys at ROOT
]
}
}
}
}
} }
])
过滤使用上一个管道的结果并检查数组大小:
db.collection.aggregate([
{ '$addFields': {
'myKeys': {
'$map': {
'input': { '$objectToArray': '$$ROOT' },
'in': {
'k': '$$this.k',
'v': {
'$cond': [ // condition to convert the _id key value in ROOT to a single element array
{ '$eq': ['$$this.k', '_id'] },
['$$this.v'],
{ '$objectToArray': '$$this.v' } // convert the rest of the keys at ROOT
]
}
}
}
}
} },
{ '$addFields':{
'myKeys': {
'$filter': {
'input': '$myKeys',
'as': 'el',
'cond': {
'$gt': [{ '$size': '$$this.v'}, 1]
}
}
}
}}
])
这可以简化为单个管道,但会减少冗长:
db.collection.aggregate([
{ '$addFields':{
'myKeys': {
'$filter': {
'input': {
'$map': {
'input': { '$objectToArray': '$$ROOT' },
'in': {
'k': '$$this.k',
'v': {
'$cond': [
{ '$eq': ['$$this.k', '_id'] },
['$$this.v'],
{ '$objectToArray': '$$this.v' }
]
}
}
}
},
'as': 'el',
'cond': {
'$gt': [{ '$size': '$$el.v'}, 1]
}
}
}
}}
])