具有嵌套结构的MongoDB查询

时间:2018-09-10 13:20:14

标签: mongodb mongodb-query pymongo-3.x

如何查询(在MongoDB中)此嵌套的json结构,以便仅获取具有“位置” 值等于“ currentPosition” 值的嵌套对象?

{  
    "JobId": "123"
    "currentPosition" : NumberInt(18), 
    "details" : [
        {
            "position": NumberInt(18),
            "fname" : "Alexander", 
            "lname" : "A",
        },
        {
            "position": NumberInt(18),
            "fname" : "Doug", 
            "lname" : "D",
        },
        {
            "position": NumberInt(15),
            "fname" : "Bruce", 
            "lname" : "B",
        },
        {
            "position": NumberInt(10),
            "fname" : "Tom", 
            "lname" : "T",
        }
    ]
}

目前,我正在通过python代码实现此目标:获取整个文档并遍历详细信息列表,以查找“ position”值等于“ currentPosition”值的对象。

最终输出看起来像

{  
    "JobId": "123"
    "currentPosition" : NumberInt(18), 
    "details" : [
        {
                "position": NumberInt(18),
                "fname" : "Alexander", 
                "lname" : "A",
            },
            {
                "position": NumberInt(18),
                "fname" : "Doug", 
                "lname" : "D",
            }
    ]
}

1 个答案:

答案 0 :(得分:0)

您将需要使用聚合框架。

details需要展开,以便您可以过滤掉不必要的细节。

$unwind阶段之后,您将有4个文档在管道中。在下一步中,您可以使用$match过滤掉您关心的细节。

这意味着您将获得2个文档,这些文档具有相同的JobIdcurrentPosition,但具有不同的details

https://docs.mongodb.com/manual/reference/operator/aggregation/unwind

db.getCollection("DELETE_ME").aggregate(
    [
        {
            $unwind: {
                path : "$details",
            }
        },
        {
            $match: {
                "$expr": {"$eq": ["$details.position", "$currentPosition"]}
            }
        },
    ]
);

会返回

{ 
    "_id" : ObjectId("---"), 
    "JobId" : "123", 
    "currentPosition" : NumberInt(18), 
    "details" : {
        "position" : NumberInt(18), 
        "fname" : "Alexander", 
        "lname" : "A"
    }
}
{ 
    "_id" : ObjectId("---"), 
    "JobId" : "123", 
    "currentPosition" : NumberInt(18), 
    "details" : {
        "position" : NumberInt(18), 
        "fname" : "Doug", 
        "lname" : "D"
    }
}