我是 MongoDB 和 Mongoose 的新手,我想在两个文档之间执行 populate() 。在查阅文档并寻找答案后,我向您寻求帮助。 我有两个型号:
备注型号
const mongoose = require('mongoose');
const noteSchema = mongoose.Schema({
_id: mongoose.Schema.Types.ObjectId,
title: {
type: String,
required: true
},
color: {
type: String,
required: true
},
position: {
type: Number,
required: true
},
isCheckBoxMode: {
type: Boolean,
required: true
},
items: [{
type: mongoose.Schema.Types.ObjectId,
ref: 'Item'
}]
}, {timestamps: true });
const Note = mongoose.model('Note', noteSchema);
module.exports = Note;
商品型号
const mongoose = require('mongoose');
const itemSchema = mongoose.Schema({
_id: mongoose.Schema.Types.ObjectId,
text: {
type: String,
required: true
},
isCompleted: {
type: Boolean,
required: true
},
noteId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'Note',
required: true
},
}, {timestamps: true });
const Item = mongoose.model('Item', itemSchema);
module.exports = Item;
在此查询中,我想使用“items”属性(引用 Item 文档)检索链接到 noteId 的所有项目的数组。正如您在上面所看到的,我确保在两个文档之间进行引用,一方面使用 items 属性及其 ref Item,另一方面使用 NoteId 属性,其 id 对应于正确的注释并引用该注释文件。
最好有例子。我正在使用 Mongo Atlas 快速部署数据库。我用 Postman 创建了一条注释,其 id 是“6553448ef2c06064f266f785”:
还有两个项目,每个项目都引用 noteId“6553448ef2c06064f266f785”:
不幸的是,当我使用 populate('items') 发送请求以检索项目内容时,我收到一个空数组:
router.get('/:noteId', (req, res, next) => {
const id = req.params.noteId;
Note.findById(id)
.populate('items')
.exec()
.then(doc => {
if (doc) {
res.status(200).json({
notes: doc,
});
}else {
res.status(404).json({message : 'No Valid entry found for provided ID'});
}
})
.catch(err => {
console.log(err);
res.status(500).json({error: err});
});
});
Postman 中的请求和响应
我找到了另一种解决方案,使用“虚拟”,但它不是最优化的解决方案,我担心会损失性能。
const mongoose = require('mongoose');
const noteSchema = mongoose.Schema({
_id: mongoose.Schema.Types.ObjectId,
title: {
type: String,
required: true
},
color: {
type: String,
required: true
},
position: {
type: Number,
required: true
},
isCheckBoxMode: {
type: Boolean,
required: true
},
}, {timestamps: true });
noteSchema.virtual('items', {
ref: 'Item',
localField: '_id',
foreignField: 'noteId'
});
noteSchema.set('toObject', { virtuals: true });
noteSchema.set('toJSON', { virtuals: true });
const Note = mongoose.model('Note', noteSchema);
module.exports = Note;
抱歉,如果我的问题有点愚蠢,但我搜索了很长时间,找不到任何解决方案。预先感谢您的帮助
我尝试链接 Mongoose 文档以及其他 Stack Overflow 帖子之后的两个文档,但没有成功。另外,我设置了一个“虚拟”,它可以工作并允许我检索所有项目,但这并未优化。另外,当我使用 POST 路由添加项目时,如果在我的请求中我还将项目的 id 添加到注释的“items”数组中,则填充有效。 但这也不是一个优化的解决方案。我想在两个“refs”之间进行简单的填充。
您的注释架构看起来不错。您有一个
items
属性,该属性已被正确定义为 mongoose.Schema.Types.ObjectId
与相应的 ref:'Note'
的数组,因此看起来像教科书。
我的建议是显式地将
path
和 model
属性传递给 populate
方法并采用 async/await
模式,如下所示:
router.get('/:noteId', async (req, res, next) => { //< Mark as async
try{
const id = req.params.noteId;
const doc = await Note.findById(id).populate({ //< use await
path: 'items', model: Item //< pass in the path and model
});
if(!doc){
return res.status(400).json({
message : 'No Valid entry found for provided ID'
});
}else{
return res.status(200).json({
notes: doc,
});
}
}catch(err){
console.log(err);
res.status(500).json({error: err});
}
});