过滤嵌套填充数组

问题描述

假设我有一个看起来像这样的教室:

{
    courseName: String,teacher: ObjectId,students: [{type: ObjectId,ref: 'Student'}]
}

“学生”模式如下所示:

{
    personalInfo: PersonalInfo,proffesionalInfo: {type: ObjectId,ref: 'ProffesionalInfo'}
}

“ProffesionalInfo”架构如下所示:

{
    allgrades: [Number],averageGrade: Number,...
    ...
}

我有教室 _id,我只想让他们的平均成绩低于 90 的学生。 我现在的做法是这样的:

Classroom.findOne({ _id })
        .populate("teacher","_id name")
        .populate({
            path: 'ridesstudents',select: 'proffesionalInfo',populate: [
                {
                    path: "proffesionalInfo",select: "allgrades averageGrade"
                }
            ]
        })
        .then(classroom => {
            classroom.students = classroom.students.filter(student => student.proffesionalInfo.averageGrade < 90);
            resolve(user);
        })
        .catch(err => reject(err));

如您所见,我在带齐所有学生后进行过滤。 如果我有 1000 万学生,只有 2 个成绩低于 90,这是“不好”的做法。

如何过滤查询中的学生而不是将所有学生都带上然后过滤??

旁注 - 以上数据只是一个示例,其目标是带来总体思路。不要深入细节。

解决方法

尝试使用聚合:

let classroom = Classroom.aggregate([
   { $match: { _id: classroomId } },{ $lookup: {
        from: "students",localField: "_id",foreignField: "students",pipeline:[
          { $lookup: {
               from: "professionalInfo",foreignField: "proffesionalInfo",as:"professionalInfo"
          }},{ $match: {$lte: ["professionalInfo.averageGrade",90]}}
        ]
        as: "students"
 }}])