假如我有两个表,一张是商品表,数据如下
/* 1 */
{
"_id" : "1",
"productName" : "java"
},
/* 2 */
{
"_id" : "2",
"productName" : "c++"
},
/* 3 */
{
"_id" : "3",
"productName" : "c#"
}
一张是订单表,一个商品对应多个订单
/* 1 */
{
"_id" : "0001",
"product_id" : "1",
"price" : 18
},
/* 2 */
{
"_id" : "0002",
"product_id" : "1",
"price" : 30
}
现在我使用lookup 连表,同时查询商品价格等于18的,我发现他把不等于18的也查询出来了,sql如下
db.test_product.aggregate([
{
"$lookup": {
"from": "test_order",
"localField": "_id",
"foreignField": "product_id",
"as": "orderList"
}
},
{
"$match": {
"_id": "1",
"orderList.price": {
"$eq": 18
}
}
},
{
"$project": {
"_id": 1,
"productName": 1,
"orderList": 1
}
}
])
结果是空集。
问题可能出在 $lookup 的 localField 和 foreignField 上。根据文档的描述,localField 是连接的左表的字段名称,而 foreignField 是右表的字段名称。在你的代码中,localField 是 "_id",而 foreignField 是 "product_id"。而在商品表中,_id 应该对应商品表中的主键字段,而 product_id 应该对应订单表中的商品字段。
如果你想在商品表中查询 id 为 1 的商品的订单,应该使用下面的查询:
db.test_product.aggregate([
{
"$lookup": {
"from": "test_order",
"localField": "_id",
"foreignField": "product_id",
"as": "orderList"
}
},
{
"$match": {
"_id": "1",
"orderList.price": {
"$eq": 18
}
}
},
{
"$project": {
"_id": 1,
"productName": 1,
"orderList": 1
}
}
])
$match 操作符中的条件需要改成
"orderList.price": {
"$eq": 18
}
这样就能获取到在订单表中,与商品表id为1且价格为18的订单信息。