$ filter然后在聚合请求mongodb上的$ project

时间:2017-11-19 12:54:05

标签: node.js mongodb aggregation-framework

我正在尝试查询我的数据库以从数组中获取特定元素,然后只投影该数组的一部分,这是我尝试过的代码:

{ $project : {
    name: 1,
    language : 1 ,
    season: [{
      $filter: {
        input: "$seasons",
        as: "s",
        cond: { $eq: [ "$$s.number", saison ] }
      }
    }, {
      $project: {
        'episodes.number': 1
      }
    }]
  } }

我想只获得与数字匹配的季节,然后仅投射数字字段。

这是我的架构:

{
  name: {type: String},
  seasons: [{
    number: Number,
    episodes: [{number: Number, videos: [
      {
        provider: String,
        quality: String,
        language: String,
        added: { type: Date, default: new Date(1510272000000)  }
      }
      ]}]
  }]
}

我当前的查询生成错误:MongoError:无法识别的表达式'$ project',如果我在没有$ project的情况下执行过滤器,但它返回一个完整的数组而不是我需要的数组。谢谢。

1 个答案:

答案 0 :(得分:3)

您的汇总管道中存在错误。你的意思是这个?

db.collectionName.aggregate([  
   {
        $project: {
            name: 1,
            language: 1,
            season: {
                $filter: {
                    input: "$seasons",
                    as: "s",
                    cond: {
                        $eq: ["$$s.number", saison]
                    }
                }
            }
        }
    },
    {
        $project: {
            'season.episodes.number': 1
        }
    }
])

如果您只想返回没有完整数组结构的单个数字:

db.collectionName.aggregate([  
   {
        $project: {
            name: 1,
            language: 1,
            season: {
                $filter: {
                    input: "$seasons",
                    as: "s",
                    cond: {
                        $eq: ["$$s.number", 1]
                    }
                }
            }
        }
    },
    { $unwind: "$season"},
    { $unwind: "$season.episodes"},
    {
        $project: {
            seasonEpisodeNumber: '$season.episodes.number'
        }
    }
])
  

无法识别的表达式'$ project'

您的第二个$project位于您的第一个$project内,这就是错误消息的原因。每个管道都是一次执行,因此您不能拥有嵌套管道。如果你需要背靠背有两个项目,那么就像那个例子那样:

{ $project: {...}}, { $project: {...}}

并且字段number位于对象字段episodes中的数组seasons内,因此您错过了。

同样在你的$filter中,不需要创建双数组。你这样做:

season: [{
      $filter: {
        input: "$seasons",
        as: "s",
        cond: { $eq: [ "$$s.number", saison ] }
      } etc...

在数组中创建一个数组。除非您期望以该形式获得结果,否则没有理由这样做。在我的回答中,我删除了嵌套数组创建。