javascript - Using aggregate $lookup and $mergeObjects - Stack Overflow

I want to join collection.before, I used only lookup, so that I could get separated field that is join

I want to join collection. before, I used only lookup, so that I could get separated field that is joined. but I need to get result similar mysql join. I noticed there is $lookup and $mergeObjects for this action but not working well.

user collection model.

{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'admin user',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 0,
            "approved": true
        },{
            "id": 2,
            "approved": true
        }
    ]
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'userOne',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 1,
            "approved": true
        }
    ]
}

roles collection model.

{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "id": '0',
    "name": 'administrator'
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "id": '0',
    "name": 'employeer'
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "id": '0',
    "name": 'freelancer'
} 

after join, I want to get result like below.

{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'admin user',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 0,
            "name": "administrator",    //join result
            "approved": true
        },{
            "id": 2,
            "name": "freelancer",       //join result
            "approved": true
        }
    ]
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'userOne',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 1,
            "name": "employeer",        //join result
            "approved": true
        }
    ]
}

I want to join collection. before, I used only lookup, so that I could get separated field that is joined. but I need to get result similar mysql join. I noticed there is $lookup and $mergeObjects for this action but not working well.

user collection model.

{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'admin user',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 0,
            "approved": true
        },{
            "id": 2,
            "approved": true
        }
    ]
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'userOne',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 1,
            "approved": true
        }
    ]
}

roles collection model.

{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "id": '0',
    "name": 'administrator'
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "id": '0',
    "name": 'employeer'
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "id": '0',
    "name": 'freelancer'
} 

after join, I want to get result like below.

{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'admin user',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 0,
            "name": "administrator",    //join result
            "approved": true
        },{
            "id": 2,
            "name": "freelancer",       //join result
            "approved": true
        }
    ]
},{
    "_id": ObjectId("xxxxxxx"), //this is default id from mongoDB
    "name": 'userOne',
    "email": '[email protected]',
    "password": 'xxxxxxxx',
    "roles": [
        {
            "id": 1,
            "name": "employeer",        //join result
            "approved": true
        }
    ]
}
Share Improve this question edited Dec 8, 2018 at 14:53 Ashh 46.6k16 gold badges111 silver badges137 bronze badges asked Apr 3, 2018 at 12:51 Android MoscowAndroid Moscow 411 silver badge4 bronze badges
Add a ment  | 

1 Answer 1

Reset to default 6

You can use below aggregation with mongodb 3.4

You need to $unwind the roles array first and then $group to rollback again

db.users.aggregate([
  { "$unwind": "$roles" },
  { "$lookup": {
    "from": "roles",
    "localField": "roles.id",
    "foreignField": "id",
    "as": "roles.role"
  }},
  { "$unwind": "$roles.role" },
  { "$addFields": {
    "roles": { "$mergeObjects": ["$roles.role", "$roles"] }
  }},
  { "$group": {
    "_id": "$_id",
    "email": { "$first": "$email" },
    "password": { "$first": "$password" },
    "roles": { "$push": "$roles" }
  }},
  { "$project": { "roles.role": 0 }}
])

Which is quite simple with the mongodb 3.6 and above

db.users.aggregate([
  { "$unwind": "$roles" },
  { "$lookup": {
    "from": "roles",
    "let": { "roleId": "$roles.id", "approved": "$roles.approved" },
    "pipeline": [
      { "$match": { "$expr": { "$eq": ["$id", "$$roleId"] }}},
      { "$addFields": { "approved": "$$approved" }}
    ],
    "as": "roles"
  }},
  { "$unwind": "$roles" },
  { "$group": {
    "_id": "$_id",
    "email": { "$first": "$email" },
    "password": { "$first": "$password" },
    "roles": { "$push": "$roles" }
  }}
])

Both will give you similar Output

[
  {
    "_id": ObjectId("5a934e000102030405000004"),
    "email": "[email protected]",
    "password": "xxxxxxxx",
    "roles": [
      {
        "_id": ObjectId("5a934e000102030405000001"),
        "approved": true,
        "id": 1,
        "name": "employeer"
      }
    ]
  },
  {
    "_id": ObjectId("5a934e000102030405000003"),
    "email": "[email protected]",
    "password": "xxxxxxxx",
    "roles": [
      {
        "_id": ObjectId("5a934e000102030405000000"),
        "approved": true,
        "id": 0,
        "name": "administrator"
      },
      {
        "_id": ObjectId("5a934e000102030405000002"),
        "approved": true,
        "id": 2,
        "name": "freelancer"
      }
    ]
  }
]

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745063607a4609117.html

相关推荐

  • javascript - Using aggregate $lookup and $mergeObjects - Stack Overflow

    I want to join collection.before, I used only lookup, so that I could get separated field that is join

    18小时前
    10

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信