【问题标题】:How to query document that has array of multiple reference in mongodb?如何在mongodb中查询具有多个引用数组的文档?
【发布时间】:2021-09-15 17:25:14
【问题描述】:

我有一个名为“assignments”的集合,如下所示:

  [
    {
        "_id" : ObjectId("60e1d5824a5b1c32c069c864"),
        "course" : ObjectId("5ffeec372b2234556439d1da"),
        "students" : [
            {
                "_id" : ObjectId("60e1d5824a5b1c32c069c865"),
                "user" : ObjectId("601e489fb77a9fabf85ea306"),
                "section" : ObjectId("6002fae3e58bc750b4394229")
            },
            {
                "_id" : ObjectId("60e1d5824a5b1c32c069c866"),
                "user" : ObjectId("601e48cdb77a9fabf85ea307"),
                "section" : ObjectId("6002fae3e58bc750b4394229")
            }
        ]
    },
    {
        "_id" : ObjectId("60e1c8a6a2886142b8b86523"),
        "students" : [
        ],
        "course" : ObjectId("5ffeec372b2234556439d1da"),
        
    }]

在这里您会看到一个名为“students”的数组。我想在查询“作业”时获取“用户”和“部分”的详细信息。

我正在使用 graphql。而“学生”是“作业”类型的字段,如下所示:

type AssignmentStudent{
    user:User
    section:Section
}

type Assignment{
    id:ID!
    createdAt:Date
    updatedAt:Date
    course:Course!
    students:[AssignmentStudent!]
}

当我查询时,我得到了“课程”的信息,但对于“学生”我不知道该怎么做。

在“作业”解析器中,我编写了这样的“课程”查询:

Assignment: {
        async course(parent, { input }, context, info) {
            try {
                return await Course.findById(parent.course)
            } catch (err) {
                console.log('err', err.message);
            }
        }
}

对于“学生”的实际结果,我该怎么办?

【问题讨论】:

  • 请展示您尝试过的任何方法以及您面临的问题。
  • 我已经更新了我的问题。你现在可以检查一下吗?

标签: node.js mongodb mongoose graphql apollo-server


【解决方案1】:

我看到您已经找到了适合您的解决方案,但是另一种方法是使用 mongoose 的填充,因为您可以具体指定您希望它返回的内容。

Assignment: {
  async course(parent, {
    input
  }, context, info) {
    try {
      return await Course.findById(parent.course).populate('students', 'user section') 
    } catch (err) {
      console.log('err', err.message);
    }
  }
}

由于您已经将它们存储为 ObjectIds(我假设参考),因此 populate 将填充您指定的字段,在本例中为学生 - 添加的第二个参数将进一步指定从中返回的内容。如果即使您的代码是正确的,您仍然存在填充问题,有时在其末尾添加 .execPopulate() 会解决问题(无法解释这一点)。

关于填充猫鼬(和指定字段)的其他一些问题/文章:

希望有帮助!

【讨论】:

    【解决方案2】:

    您只需要遍历学生数组并为每个项目创建类似的 findOne。或者你可以过滤 id 并 make find({ _id: { $in: ['1', '2', '3'] } }),然后附加结果。

    【讨论】:

      【解决方案3】:

      实际上,我采用了类似下面的方法,它对我有用。我不确定这种方法是否有效,但它确实有效。

      async students(parent, { input }, context, info) {
                  try {
      
                      const promises = parent.students.map(async (item) => {
                          return {
                              id: item.id,
                              user: await User.findById(item.user),
                              section: await Section.findById(item.section)
                          }
                      });
                      return Promise.all(promises);
                  } catch (err) {
                      console.log('err', err.message);
                  }
              },
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-06-06
        • 1970-01-01
        • 2014-01-16
        • 2020-11-17
        • 1970-01-01
        • 2017-09-13
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多