聚合$filter在$lookup之后不起作用



我试图在查找操作符之后过滤数据。我没有得到预期的行为从我的查询。

我的网关集合是

{ "_id" : "18001887", "mac_id" : "18001887", group_id: "0" }
{ "_id" : "18001888", "mac_id" : "18001888", group_id: "1" }
{ "_id" : "18001889", "mac_id" : "18001889", group_id: "0" }

我的命令集合是

{
"_id" : ObjectId("615581dcb9ebca6c37eb39e4"),
"org_id" : 0,
"mac_id" : "18001887",
"config" : {
"user_info" : [ 
{
"user_id" : 1,
"user_pwd" : "123456",
"mapped_id" : 1
}, 
{
"user_id" : 2,
"user_pwd" : "123123",
"mapped_id" : 3
}
]
}
}
{
"_id" : ObjectId("615581dcb9ebca6c37eb39e4"),
"org_id" : 0,
"mac_id" : "18001889",
"config" : {
"slave_id" : 1 
}
}

我想获取网关group_id = 0和"config.user_info.mapped_id"= 1。我写了下面的查询,但它似乎不工作

gateway_model.aggregate([
{
$match: {
group_id: "0"
},

},
{
$project: {
_id: 0,
mac_id: 1
}
},
{
$lookup: {
from: "commands",
localField: "mac_id",
foreignField: "mac_id",
as: "childs"

}
},
{ 
$project: {
mac_id: 1,
childs: {
$filter: {
"input": "$childs",
"as": "child",
"cond": {"$eq": ["$$child.config.user_info.mapped_id", 1]},
}
}
}
}
])

上面的查询返回group_id为0的网关,child为空数组。

字段user_info是数组,您正在检查$filter操作中的相等条件,您可以按照以下方式更改$filter条件,

  • 当我们从数组字段$$child.config.user_info.mapped_id访问mapped_id时,它将返回id数组,因此我们需要使用$in条件
  • $ifNull检查user_info字段是否不存在,然后返回空白数组
  • $in操作符检查mapped_id的数组
{
$project: {
mac_id: 1,
childs: {
$filter: {
"input": "$childs",
"as": "child",
"cond": {
"$in": [
1,
{ $ifNull: ["$$child.config.user_info.mapped_id", []] }
]
}
}
}
}
}

游乐场


第二个选项,这是处理这种情况的正确方法,$lookup使用管道,

  • letmac_id传递给管道
  • 检查$exprmac_id条件
  • 匹配mapped_id条件
db.gateway.aggregate([
{ $match: { group_id: "0" } },
{
$lookup: {
from: "commands",
let: { mac_id: "$mac_id" },
pipeline: [
{
$match: {
$expr: { $eq: ["$mac_id", "$$mac_id"] },
"config.user_info.mapped_id": 1
}
}
],
as: "childs"
}
},
{
$project: {
_id: 0,
mac_id: 1,
childs: 1
}
}
])

游乐场

如果你想过滤user_info数组,那么你可以在$lookup阶段的$match阶段之后再添加一个阶段,

{
$addFields: {
"config.user_info": {
$filter: {
input: "$config.user_info",
cond: { $eq: ["$$this.mapped_id", 1] }
}
}
}
}

游乐场

相关内容

  • 没有找到相关文章

最新更新