Ognjen Kljajic
Ognjen Kljajic

Reputation: 37

Mongodb lookup with match in aggregate returns an empty array

This is my user document

{
   "_id":"02a33b9a-284c-4869-885e-d46981fdd679",
   "context":{
      "email":"[email protected]",
      "firstName":"John",
      "lastName":"Smith",
      "company":[
         "e2467c93-114b-4613-a842-f311a8c537b3"
      ],
   },
}

and a company document

{
   "_id":"e2467c93-114b-4613-a842-f311a8c537b3",
   "context":{
      "name":"Coca Cola",
      "image":"someimage",
   },
};

This is my query for users

let users = await Persons.aggregate(
            [{$project:
            {
                name: {$concat: ['$context.firstName', ' ', '$context.lastName']},
                companyId: {$arrayElemAt: ['$context.company', 0]}}
            },
            {$match: {name: searchRegExp}},
            {$lookup: {from: 'companies', let: {company_id: {$arrayElemAt: ['$context.company', 0]}}, pipeline:
            [
                {
                    $match: {
                        $expr: {
                            $eq: ['$_id', '$$company_id']
                        }
                    }
                },
                {
                    $project: {name: '$context.name'}
                }
            ],
            as: 'company'}}
            ]).toArray()

When I run this query I get company field as an empty array, what am I doing wrong here?

Upvotes: 1

Views: 720

Answers (2)

Wernfried Domscheit
Wernfried Domscheit

Reputation: 59456

When you add field companyId: {$arrayElemAt: ['$context.company', 0]}}, then you can use the simple version of $lookup. There is no need to set it twice, once as companyId: ... and in let: {company_id: ...}

db.user.aggregate([
   {
      $addFields: {
         name: { $concat: ["$context.firstName", " ", "$context.lastName"] },
         companyId: { $arrayElemAt: ["$context.company", 0] } 
      }
   },
   {
      $lookup: {
         from: "company",
         localField: "companyId",
         foreignField: "_id",
         as: "company"
      }
   }
])

Upvotes: 1

mickl
mickl

Reputation: 49945

Your first pipeline stage $project only outputs _id, name and companyId so then when you're trying to refer to $context.company in your $lookup there will be an empty value. You can use $addFields instead:

{
    $addFields: {
        name: {
            $concat: [
                "$context.firstName",
                " ",
                "$context.lastName"
            ]
        },
        companyId: {
            $arrayElemAt: [
                "$context.company",
                0
            ]
        }
    }
}

Mongo Playground

Upvotes: 2

Related Questions