You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MongoDB聚合查询中如何过滤$lookup关联的未审核餐厅评论?

解决方案

以下是修正后的MongoDB聚合查询代码,可实现仅获取关联已审核餐厅的用户评论:

const users = await db
  .collection('users')
  .aggregate([
    {
      $lookup: {
        from: 'restaurants',
        let: { reviewRestaurantIds: '$reviews._restaurantId' },
        pipeline: [
          {
            $match: {
              $expr: {
                $and: [
                  { $in: ['$_id', '$$reviewRestaurantIds'] },
                  { $eq: ['$isApproved', true] }
                ]
              }
            }
          }
        ],
        as: 'approvedRestaurants'
      }
    },
    {
      $project: {
        name: 1,
        surname: 1,
        image: 1,
        reviews: {
          $filter: {
            input: {
              $map: {
                input: '$reviews',
                as: 'review',
                in: {
                  $mergeObjects: [
                    '$$review',
                    {
                      restaurant: {
                        $arrayElemAt: [
                          '$approvedRestaurants',
                          { $indexOfArray: ['$approvedRestaurants._id', '$$review._restaurantId'] }
                        ]
                      }
                    }
                  ]
                }
              }
            },
            as: 'mappedReview',
            cond: { $ne: ['$$mappedReview.restaurant', null] }
          }
        }
      }
    },
    {
      $match: {
        'reviews.0': { $exists: true }
      }
    },
    { $unwind: '$reviews' },
    { $sort: { 'reviews.date': -1 } },
    {
      $group: {
        _id: '$_id',
        name: { $first: '$name' },
        surname: { $first: '$surname' },
        image: { $first: '$image' },
        reviews: { $push: '$reviews' }
      }
    },
    { $limit: 12 }
  ])
  .toArray();

关键修改说明

  • 修正$lookup逻辑:
    原写法同时使用localField/foreignField和pipeline属于MongoDB语法错误(引擎会忽略前两者),改用let传递用户的评论餐厅ID数组,在管道内通过$expr关联ID并过滤已审核餐厅,确保approvedRestaurants仅包含符合条件的数据。

  • 过滤无效评论:
    先通过$map为每条评论匹配对应的已审核餐厅,再用$filter剔除匹配失败(餐厅为null)的评论,直接过滤掉指向未审核餐厅的内容。

  • 调整用户过滤时机:
    将$match移到$project之后,通过'reviews.0': { $exists: true }确保只保留至少有一条有效评论的用户,避免无意义数据进入后续分组排序流程。

  • 简化餐厅信息映射:
    直接将匹配到的餐厅对象赋值给restaurant字段,若前端仅需特定属性,可在$arrayElemAt内嵌套$project调整返回字段,例如:

    restaurant: {
      $arrayElemAt: [
        { $project: { 'basics.name': 1, 'location.city': 1, 'location.state': 1 }, '$approvedRestaurants' },
        { $indexOfArray: ['$approvedRestaurants._id', '$$review._restaurantId'] }
      ]
    }
    

内容的提问来源于stack exchange,提问作者Ravenwits

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.24 02:05:25