大家好,
我使用的是猫鼬版本 5.0.3 和节点版本 9.4.0。 根据 mongoose 文档,model.create 应该返回一个承诺,我假设该承诺在创建的文档保存在数据库中时得到解决。 但是,如下面的代码所示,似乎在将文档保存在数据库中之前就解决了承诺。
async function test(){
let schema = new mongoose.Schema({a: String});
let model = mongoose.model('test', schema);
await model.remove({}).exec();
await model.create({ a: 'test'},
(err,result)=> {console.log('created');});
await model.findOneAndUpdate(
{ a : 'test' } ,
{ a: 'newValue'}
)
.exec((err, result) => {
console.log('update : '+result);
});
await model.find({a: 'test'},(err,result) => {
console.log(result);
});
}
output in terminal :
update : null
found :
created
findOneAndUpdate 没有找到任何文件。 除了“created”出现在终端的末尾之外,因此 create 方法的回调被执行,就好像 await 没有等待异步任务“create”完成一样。
但是通过添加一个 promise,一旦 create 的回调被触发,它就会被解析,如下所示,我们得到了预期的结果:
async function test(){
let schema = new mongoose.Schema({a: String});
let model = mongoose.model('test', schema);
await model.remove({}).exec();
await new Promise((resolve,reject) => {
model.create({ a: 'test'},
(err,result)=> {
console.log('created');
resolve();
});
});
await model.findOneAndUpdate(
{ a : 'test' } ,
{ a: 'newValue'}
)
.exec((err, result) => {
console.log('update : '+result);
});
await model.find({a: 'newValue'},(err,result) => {
console.log('found : ' +result);
});
}
output in terminal:
created
update : { _id: 5a735fbc1fe826233014d62d, a: 'test', __v: 0 }
found : { _id: 5a735fbc1fe826233014d62d, a: 'newValue', __v: 0 }
现在我们有了预期的结果。
所有对 DB 进行操作的函数都会返回一个承诺,如果解决了就表明操作已经完成,特别是 Query。 我认为这也是 model.create 的情况,尽管严格来说它不返回查询对象。 我也想知道已履行的返回承诺意味着什么,因为它没有显示该文档是在数据库中创建的。 也许我错过了整点,但我发现它有点模棱两可
我相信我记得在 4.x 文档中读到,如果您将回调传递给 model.create 它不会返回承诺。
let x = model.create({ a: 'test' }, () => {})
x.then(console.log(x)) //TypeError: Cannot read property 'then' of undefined
如果你拉出回调:
let x = model.create({ a: 'test' })
x.then(console.log(x)) // Promise { <pending> }
model.js 的 5.x 源代码支持调用 utils.promiseOrCallback
是的, @lineus是正确的,我可以关闭这个问题@CodeurSauvage吗?
@CodeurSauvage @lineus是正确的,猫鼬5如果指定了回调不返回的承诺。 如果您替换,您的脚本将起作用:
await model.create({ a: 'test'},
(err,result)=> {console.log('created');});
和:
await model.create({ a: 'test'}).then(result => console.log('created'));
最有用的评论
我相信我记得在 4.x 文档中读到,如果您将回调传递给 model.create 它不会返回承诺。
如果你拉出回调:
model.js 的 5.x 源代码支持调用 utils.promiseOrCallback