【问题标题】:Accessing nested documents within nested documents在嵌套文档中访问嵌套文档
【发布时间】:2018-09-19 00:27:35
【问题描述】:

我遇到了一个非常困扰我的问题。我什至不想使用这个我不认为的解决方案,但我想知道是否有。

我正在使用 mongodb 和 mongoose 创建一个评论部分,并像这样将 cmets 附加到资源:

const MovieSchema = new mongoose.Schema({
  movieTitle: {type: String, text: true},
  year: Number,
  imdb: String,
  comments: [{
    date: Date,
    body: String
  }]
})

在编辑 cmets 正文时,我知道我可以访问这样的嵌套文档:

const query = {
    imdb: req.body.movie.imdb,
    "comments._id": new ObjectId(req.body.editedComment._id)
}

const update = {
    $set: {
        "comments.$.body": req.body.newComment
    }
}

Movie.findOneAndUpdate(query, update, function(err, movie) {
    //do stuff
})

然后我想推出对 cme​​ts 的第一级回复,其中对评论或另一个回复的每条回复都只是作为顶级评论的回复数组出现(有点像 Facebook,而不像 reddit)。起初,我希望将回复附加到 cmets,就像我将 cmets 附加到资源一样。所以架构看起来像这样:

const MovieSchema = new mongoose.Schema({
    movieTitle: {type: String, text: true},
    year: Number,
    imdb: String,
    comments: [{
        date: Date,
        body: String,
        replies: [{
            date: Date,
            body: String
        }]
    }]
})

我的问题是您将如何访问嵌套的嵌套文档。例如,如果我想编辑回复,我似乎不能使用两个 $ 符号。那么我将如何在 mongodb 中做到这一点,这甚至可能吗?

我很确定我会让 Comments 有自己的模型来简化事情,但我仍然想知道这是否可能,因为如果不是,这似乎是 mongodb 的一个很大的缺点。另一方面,如果我不知道如何编辑嵌套的嵌套文档,我会觉得使用 mongodb 很愚蠢......

【问题讨论】:

  • comments.$.replies.$.date 这样的更新查询有什么问题?到目前为止你尝试了什么?你得到什么错误?你的数据集在哪里?

标签: mongodb express mongoose nested-documents


【解决方案1】:

根据这个问题:https://jira.mongodb.org/browse/SERVER-27089

可以通过这种方式更新嵌套的嵌套元素:

parent.update({}, 
    {$set: {“children.$[i].children.$[j].d”: nuValue}}, 
    { arrayFilters: [{ “i._id”: childId}, { “j._id”: grandchildId }] });

这包含在 MongoDB 3.5.12 开发版和 MongoDB 3.6 生产版中。

根据https://github.com/Automattic/mongoose/issues/5986#issuecomment-358065800,它应该在 mongoose 5+ 中得到支持


如果您使用的是较旧的 mongodb 或 mongoose 版本,则有 2 个选项:

查找父级,编辑结果的孙级,保存父级。

const result = await parent.findById(parentId);

const grandchild = result.children.find(child => child._id.equals(childId))
    .children.find(grandchild => grandchild._id.equals(grandchildId));

grandchild.field = value;

parent.save();

“不知何故”知道孙子的索引,findByIdAndUpdate 父级:

parent.findByIdAndUpdate(id,
    { $set: { [`children.$.children.${index}.field`]: value }});

【讨论】:

    猜你喜欢
    • 2018-03-09
    • 2020-11-29
    • 1970-01-01
    • 2021-11-12
    • 2019-04-29
    • 1970-01-01
    • 2018-07-14
    • 1970-01-01
    • 2013-06-12
    相关资源
    最近更新 更多