使用猫鼬,我的 populate 方法有问题

问题描述 投票:0回答:1

我在 nextjs 应用程序中使用猫鼬,并且在特定情况下填充方法有问题。 让我用下面的代码解释一下:

这是我的代码: 第一个模型

import mongoose, { Schema } from "mongoose";

const muscleSchema = new Schema(
  {
    name: {
      type: String,
      required: [true, "Name is required"],
      trim: true,
      enum: ['legs', 'glutes', 'back', 'abs', 'pectorals', 'arms', 'shoulders'],
    },
  }
);

const Muscle = mongoose.models.Muscle || mongoose.model("Muscle", muscleSchema)

export default Muscle;

第二型号:

import mongoose, { Schema } from "mongoose";

const exerciseSchema = new Schema(
  {
    name: {
      type: String,
      required: [true, "Name is required"],
      trim: true,
    },
    muscle: {
      type: mongoose.Schema.Types.ObjectId,
      ref: 'Muscle',
      required: true,
    }
  }
);

const Exercise = mongoose.models.Exercise || mongoose.model("Exercise", exerciseSchema)

export default Exercise;

这是我获得 ONE Exercice 的“exercise”路线 api :

export async function GET(request, { params }) {
  try {
    const { id } = params;
    await connectDb();
    const exercise = await Exercise.findById(id);
    await exercise.populate({ path: "muscle", select: "name" });
    console.log(exercise)
    return NextResponse.json(exercise, { status: 200 });
  } catch (err) {
    const { errors } = err;
    return NextResponse.json(errors, { status: 404 });
  }
}

它工作得很好,我明白了:

{
    "_id": "6559e924d02b9f36fd7f574d",
    "name": "squats",
    "muscle": {
        "_id": "65101d9667cb93cb766bfe79",
        "name": "legs"
    },
    "__v": 0
}

但是当我想通过这条路线通过肌肉ID进行一些练习时,填充dosen似乎不起作用:

export async function GET(request, { params }) {
  try {
    const muscle_id = request?.url.split("=")[1];
    await connectDb();
    const findExercises = async () => {
      if (muscle_id) {
        console.log(muscle_id);
        return Exercise.find({ muscle: muscle_id });
      }
      return Exercise.find();
    };
    console.log("before", await findExercises());
    const exercises = await findExercises();
    exercises.map(async (exercice) => {
      return await exercice.populate({
        path: "muscle",
        select: "name",
      });
    });
    console.log("after", exercises);
    return NextResponse.json(exercises, { status: 200 });
  } catch (err) {
    const { errors } = err;
    return NextResponse.json(errors, { status: 404 });
  }
}

这是我的回应:

[
    {
        "_id": "6559e924d02b9f36fd7f574d",
        "name": "squats",
        "muscle": "65101d9667cb93cb766bfe79",
        "__v": 0
    },
    {
        "_id": "6559f1f2d02b9f36fd7f57ab",
        "name": "deadlift",
        "muscle": "65101d9667cb93cb766bfe79",
        "__v": 0
    }
]

但我应该有类似的东西:

[
    {
        "_id": "6559e924d02b9f36fd7f574d",
        "name": "squats",
        "muscle": {
        "_id": "65101d9667cb93cb766bfe79",
        "name": "legs"
    },
        "__v": 0
    },
    {
        "_id": "6559f1f2d02b9f36fd7f57ab",
        "name": "deadlift",
        "muscle": {
        "_id": "65101d9667cb93cb766bfe79",
        "name": "legs"
    },
        "__v": 0
    }
]

有人可以帮助我吗?

node.js mongoose next.js mongoose-populate
1个回答
0
投票

我不太确定您为什么创建函数

findExercises()
来检查
muscle_id
。您可以在正常控制流中执行此操作,并根据
if
的条件结果确定查询对象。

您的

map
函数也没有执行您期望的操作,想象一下,如果您的
find
结果返回数十万甚至数百万个文档(这发生在生产环境中),那么您将为每个文档执行一次数据库请求在那张地图里。如果这是一条每分钟接收数百或数千个请求的繁忙路线,您的应用程序将承受巨大的压力。

无论如何,

Model.find()
方法可以采用空查询对象,因此实现这些更改,希望您能得到所需的结果:

try {
   const muscle_id = request?.url.split("=")[1];
   await connectDb();
   // If muscle_id truthy then create query on muscle property 
   // else create empty query
   const query = muscle_id ? { muscle: muscle_id } : {};
   const exercises = await Exercise.find(query).populate({ 
      path: "muscle", 
      select: "name" 
   });
   return NextResponse.json(exercises, { status: 200 });
} catch (err) {
   const { errors } = err;
   return NextResponse.json(errors, { status: 404 });
}
© www.soinside.com 2019 - 2024. All rights reserved.