代码之家  ›  专栏  ›  技术社区  ›  metamemelord

从嵌套对象投影展开值

  •  0
  • metamemelord  · 技术社区  · 7 年前

    例如:

    以下是一个示例文档:

    {
        "location": "eindhoven",
        "partners": [
            {
                "partner_id": 3,
                "passed_tests": true
            },
            {
                "partner_id": 2,
                "passed_tests": false
            }
        ],
        "_id": "3136323031333066306d4438",
        "uid": "d95f2e446c052514c097e6c925408774",
        "__v": 0,
        "is_approved": true
    }
    

    我的代码如下:

    function returnAll(callback) {
        TestService.aggregate([
            {
                $match: { "is_approved": true }
            },
            {
                $unwind: "$partners"
            }, {
                $group: {
                    "_id": {
                        partner: { $objectToArray: "$partners" },
                        partner_id: { $arrayElemAt: ["$partner", 0] }
                    },
                    "count": { "$sum": 1 }
                }
            },
            {
                $sort: { "count": -1 }
            },
            {
                $project: {
                    "partner_values": {
                        $map: {
                            input: "$_id.partner",
                            as: "el",
                            in: {
                                $cond: {
                                    if: {
                                        $or: [{ $eq: ["$$el.v", true] },
                                        { $eq: ["$$el.v", false] }]
                                    }, then: {
                                        "passed_tests": "$$el.v"
                                    }, else: {
                                        "id": "$$el.v"
                                    }
                                }
                            }
                        }
                    },
                    "count": "$count,
                    "_id": 0
                }
            },
        ], function (error, data) {
            if (error) {
                logger.error(error);
                callback(null);
            } else {
                callback(data);
            }
        });
    }
    

    将此JSON返回到我的节点应用程序:

    "data": [
            {
                "partner_values": [
                    {
                        "id": 2
                    },
                    {
                        "passed_tests": false
                    }
                ],
                "count": 3
            },
            {
                "partner_values": [
                    {
                        "id": 6
                    },
                    {
                        "passed_tests": true
                    }
                ],
                "count": 1
            },
            {
                "partner_values": [
                    {
                        "id": 3
                    },
                    {
                        "passed_tests": true
                    }
                ],
                "count": 1
            },
            {
                "partner_values": [
                    {
                        "id": 1
                    },
                    {
                        "passed_tests": true
                    }
                ],
                "count": 1
            }
        ]
    

    如果我不在聚合中使用投影管道,我会得到以下结果:

    "data": [
            {
                "_id": {
                    "partner": [
                        {
                            "k": "partner_id",
                            "v": 2
                        },
                        {
                            "k": "passed_tests",
                            "v": false
                        }
                    ],
                    "partner_id": null
                },
                "count": 3
            },
            {
                "_id": {
                    "partner": [
                        {
                            "k": "partner_id",
                            "v": 6
                        },
                        {
                            "k": "passed_tests",
                            "v": true
                        }
                    ],
                    "partner_id": null
                },
                "count": 1
            },
            {
                "_id": {
                    "partner": [
                        {
                            "k": "partner_id",
                            "v": 3
                        },
                        {
                            "k": "passed_tests",
                            "v": true
                        }
                    ],
                    "partner_id": null
                },
                "count": 1
            },
            {
                "_id": {
                    "partner": [
                        {
                            "k": "partner_id",
                            "v": 1
                        },
                        {
                            "k": "passed_tests",
                            "v": true
                        }
                    ],
                    "partner_id": null
                },
                "count": 1
            }
        ]
    

    "data": {
                "partners": [{
                    "id": 2,
                    "passed_tests": false,
                    "count": 3
                }, {
                    "id": 6,
                    "passed_tests": false,
                    "count": 1
                }, {
                    "id": 3,
                    "passed_tests": false,
                    "count": 1
                }, {
                    "id": 1,
                    "passed_tests": false,
                    "count": 1
                }]
            }
    

    1 回复  |  直到 7 年前
        1
  •  1
  •   s7vr    7 年前

    您可以使用下面的聚合查询。

    TestService.aggregate([
      {"$match":{"is_approved":true}},
      {"$unwind":"$partners"},
      {"$group":{
        "_id":{"partner_id":"$partners.partner_id","passed_tests":"$partners.passed_tests"},
        "count":{"$sum":1}
      }},
      {"$sort":{"count":-1}},
      {"$group":{
        "_id":null,
        "partners":{"$push":{"id":"$_id.partner_id","passed_tests":"$_id.passed_tests","count":"$count"}}
      }},
      {"$project":{"partners":1}}
    ])