我有一个包含以下格式文档的集合:
{
"_id" : ObjectId("abc"),
"mobile" : "123456789",
"channels" : [
{
"name" : "email.xz",
"type" : "a",
"properties" : [
{
"provider" : "outlook"
}
]
},
{
"name" : "sms",
"type" : "sms"
}
],
}
我需要找到至少有一个名称以“.xz”结尾的渠道的客户,但仅限于提供商存在且具有值,并返回每个渠道的客户数。例如:
email.xz = 10
sms.xz = 5
push.xz = 7
我尝试使用下面的聚合函数,但它会计算出符合条件的所有客户。
db.consumers.aggregate(
{$match: {"channels.name": {$regex: ".xz$"},
"notificationChannels.properties.provider": { $exists: true }}},
{$group: {_id: "channels.name"},
count: {$sum: 1}})
答案 0 :(得分:2)
$unwind
数组,然后$match
再次以同样的方式。第一场比赛只是选择文档,您想要过滤:
db.consumers.aggregate(
{ $match: {
"channels.name": {$regex: ".xz$"},
"channels.properties.provider": { $exists: true }
}},
{ $unwind: "$channels" },
{ $match: {
"channels.name": {$regex: ".xz$"},
"channels.properties.provider": { $exists: true }
}},
{ $group:{
"_id": "$channels.name",
"count": {$sum: 1}
}}
)
由于您希望对数组“内部”的某个键进行$group
,因此无论如何都需要$unwind
。由于您只需要符合条件的数组条目,因此使用$regex
进行此操作的唯一方法是$match
之后的$unwind