MongoDB
 sql >> Base de Dados >  >> NoSQL >> MongoDB

Como juntar e classificar algumas coleções em um pipeline no Mongo


Última versão do Mongo 3.4, você usará $ faceta para processar os mesmos dados em vários pipelines de agregação e unir o resultado de todas as agregações a uma única saída.
db.users.aggregate([
    { "$match": { "_id":1} },
    {
        "$facet": {
            "Received": [
                 {$lookup: {from: 'requests', localField: "_id", foreignField: "userId", as: "receivedRequest"}},
                 {$unwind: '$receivedRequest'},
                 {$lookup: {from: 'users', localField: "receivedRequest.requesterId", foreignField: "_id", as: "receivedUser"}},
                 {$project: {_id: '$receivedRequest.requesterId', profile: '$receivedUser.profile', weight: {$add: [4]}}}
            ],
            "Sent": [
                 {$lookup: {from: 'requests', localField: "_id", foreignField: "requesterId", as: "sentRequest"}},
                 {$unwind: '$sentRequest'},
                 {$lookup: {from: 'users', localField: "sentRequest.userId", foreignField: "_id", as: "sendUser"}},
                 {$project: {_id: '$sentRequest.userId', profile: '$sendUser.profile', weight: {$add: [3]}}}
            ],
            "Friends": [
                 {$lookup: {from: 'friends', localField: "_id", foreignField: "userId", as: "friends"}},
                 {$unwind: '$friends'},
                 {$lookup: {from: 'users', localField: "friends.friendId", foreignField: "_id", as: "friendUser"}},
                 {$project: {_id: '$friends.friendId', profile: '$friendUser.profile', weight: {$add: [2]}}}
            ],
            "Others": [
                {$lookup: {from: 'friends', localField: "_id", foreignField: "friendId", as: "others"}},
                 {$unwind: '$others'},
                 {$lookup: {from: 'users', localField: "others.userId", foreignField: "_id", as: "other"}},
                 {$project: {_id: '$others.userId', profile: '$other.profile', weight: {$add: [1]}}}
            ]
        }
    }
]).pretty()

Saída de amostra:
{
        "Received" : [
                {
                        "_id" : 3,
                        "profile" : [
                                {
                                        "name" : "John"
                                }
                        ],
                        "weight" : 4
                }
        ],
        "Sent" : [
                {
                        "_id" : 4,
                        "profile" : [
                                {
                                        "name" : "Jessica"
                                }
                        ],
                        "weight" : 3
                }
        ],
        "Friends" : [
                {
                        "_id" : 2,
                        "profile" : [
                                {
                                        "name" : "Ana"
                                }
                        ],
                        "weight" : 2
                }
        ],
        "Others" : [
                {
                        "_id" : 5,
                        "profile" : [
                                {
                                        "name" : "Sheldon"
                                }
                        ],
                        "weight" : 1
                }
        ]
}