来自多个集合的 $lookup 的 Mongoose 聚合返回空集

Posted

技术标签:

【中文标题】来自多个集合的 $lookup 的 Mongoose 聚合返回空集【英文标题】:Mongoose aggregate with $lookup from multiple collections returning empty set 【发布时间】:2021-10-25 05:03:06 【问题描述】:

我有 3 个收藏:

    用户 公司 商店

用户和商店对公司有对象引用。

用户: company: type: Schema.Types.ObjectId, ref: 'Company'

商店: parentCompany: type: Schema.Types.ObjectId, ref: 'Company'

我正在尝试对公司进行简单聚合,并希望拥有给定公司的所有用户和商店。

companyModel.aggregate(
        [
             $match:  _id: 'companyidhere123445'  ,
            
                $lookup: 
                    from: 'stores',
                    localField: '_id',
                    foreignField: 'parentCompany',
                    as: 'stores',
                
            ,
             $unwind: '$stores' ,
            
                $lookup: 
                    from: 'users',
                    localField: '_id',
                    foreignField: 'company',
                    as: 'users',
                
            ,
             $unwind: '$users' ,
        ]);

我得到一个空数组。 (是的,我测试了 id 匹配,model.find 为相同的 id 返回公司,是的,用户和商店分别匹配 companyparentCompany 字段上的 id。我已经检查了可能的重复项,但我不能弄清楚我在做什么不同,但我的聚合返回为空。在 mongoose 和 mongo shell 中测试了相同的查询。没有错误,没有警告。)

【问题讨论】:

你是匹配 _id 作为 ObjectId 还是字符串格式? 您是否尝试通过删除阶段进行调试。你也可以使用mongodb compass 来构建更好的聚合 我确实删除了阶段,但结果相同,直到我下班。 @fractal397:不,id 是 ObjectId,正如我提到的,相同的 id 返回公司,或者用户或商店分开就好了。 @fractal397 :你的怀疑是对的。 :) 【参考方案1】:

解决了! (我猜是那些日子!)

id 在 req.params 中,尽管这对于 findOne 或 findById 之类的查询很有效,但它不适用于聚合,因此在匹配中使用之前,我必须将其重铸为 mongoose 对象 id:

const matchId = mongoose.Types.ObjectId(req.params.id);

然后:

 $match:  _id: matchId  ,

瞧! (我在哪里可以看到用头敲击键盘的动图?)

【讨论】:

以上是关于来自多个集合的 $lookup 的 Mongoose 聚合返回空集的主要内容,如果未能解决你的问题,请参考以下文章

来自多个集合的 $lookup 的 Mongoose 聚合返回空集

如何在 mongodb 中使用 $lookup 加入多个集合

Mongoose.aggregate(pipeline) 使用 $unwind、$lookup、$group 链接多个集合

$lookup 结果使用来自另一个数组的键排序

MongoDb $elemMatch 与 $lookup 变量

$lookup 没有 $unwind 的多个级别?