我偶然发现行中的猫鼬文档
猫鼬查询不是承诺。他们有一个.then()函数 和async / await为方便。如果您需要完整的承诺, 使用.exec()函数。
在此示例中
var query = Band.findOne({name: "Guns N' Roses"});
assert.ok(!(query instanceof Promise));
// A query is not a fully-fledged promise, but it does have a `.then()`.
query.then(function (doc) {
// use doc
});
// `.exec()` gives you a fully-fledged promise
var promise = query.exec();
assert.ok(promise instanceof Promise);
promise.then(function (doc) {
// use doc
});
现在,当他们说全面承诺时,我并没有理解他们的意思,就像对我.then()
来说应该是一种提倡,然后它还允许异步和等待。
那么有人可以向我解释完全承诺的意思是什么吗?
参考链接:https://mongoosejs.com/docs/promises.html#queries-are-not-promises
答案 0 :(得分:6)
这意味着,根据Promises/A+ spec的定义,查询返回的值是 thenables ,而不是实际的Promise
实例。这意味着它们可能不具有Promise的所有功能(例如,catch
和finally
方法)。实际的Promise
实例将是“完全成熟的”承诺。
英语术语“ fully-fledged”表示“完整”或“完全开发”。它来自鸟类学(或至少与鸟类有关的术语):一只成年羽毛的小鸡(一只幼鸟)“出雏”;如果它的所有成年羽毛都完全覆盖了down底毛,则说明它是成熟的。
答案 1 :(得分:0)
@ T.J。 Crowder的回答确实帮助我澄清了很多事情(我也碰到了这个帖子,因为我也很困惑),我只想在这里补充一点:)
传统上,then()方法返回Promise。它最多包含两个参数:Promise的成功情况(onFulfilled)和失败情况(onRejected)的回调函数。然而,罐头食品无法以这种方式工作。我们将无法传递两个回调函数,例如我们如何使用“完全承诺”。用一些代码来说明这一点:
UserModel.find().exec((err, users) => {
if (err) return res.status(400).send(err);
res.status(200).json({
success: true,
users,
});
});
这很好用,因为我们为成功案例和失败案例传入的两个回调函数称为err(失败案例),而成功/结果案例称为用户。 请注意,Mongoose中的所有回调都使用以下模式:callback(error,result)-这与MDN Web文档中指定的回调函数的顺序不同。现在,如果我们运行同一段代码,但是用then()替换exec()就像这样:
UserModel.find().then((err, users) => {
if (err) return res.status(400).send(err);
res.status(200).json({
success: true,
users,
});
});
这将返回400错误的请求状态。
这是因为猫鼬查询不是“完整的承诺”,因此我们不能在查询后链接.then(),然后期望它像真正的承诺一样。
但是,根据我的尝试,实际上,您仍然可以像这样使用.catch()
进行错误处理:
// {_id:1} is included to make this fail
UserModel.find({ _id: 1 })
.then((users) => {
res.status(200).json({
success: true,
users,
});
})
.catch((err) => {
res.status(400).send(err);
});