我有一个 nodejs 后端,使用 Mongoose 快速处理我的 API 到我的 mongo 数据库的路由。我更改了代码,使其更易于理解,但本质上我是在构建任务列表。
我有一个用于将任务添加到任务列表的端点,我想维护一个任务列表以便稍后执行一些分析。我遇到的问题是我想检查一个任务是否已经存在,如果该任务不存在,那么我想在我的任务模型中创建它,然后将它添加到我的任务列表中。如果它确实存在,那么我只想将它添加到我的任务列表中。
我的第一个想法是在创建任务时在保存操作上使用异步,因为我想避免嵌套大量的 promise ,因为这会使它变得非常不可读。但是当我的 nodejs 服务器启动时,它给我一个错误 SyntaxError: await is only valid in async function
但是从文档中你可以使用 await on save,并且我的函数有 async 关键字。所以我不知道我做错了什么。
exports.tasklists_add_task = async (req, res, next) => {
const id = req.params.tasklistId;
Task.findOne({ externalId: req.body.externalId })
.exec()
.then(doc => {
let task = doc;
if (!task) {
task = new Task({
_id: new mongoose.Types.ObjectId(),
externalId: req.body.externalId,
name: req.body.name
});
await task.save();
}
tasklist.update({_id: id}, {$push: { tasks: tasks }})
.select("-__v")
.exec()
})
.then(result => {
...
})
.catch(err => { ... })
}
我有 2 个模式一个任务模式
const mongoose = require("mongoose");
const taskSchema = mongoose.Schema({
_id: mongoose.Schema.Types.ObjectId,
externalId: { type: String, required: true },
name: { type: String, required: true }
});
module.exports = mongoose.model("Task", taskSchema);
和一个任务列表模式
const mongoose = require("mongoose");
const taskListSchema = mongoose.Schema({
_id: mongoose.Schema.Types.ObjectId,
user: { type: mongoose.Schema.Types.ObjectId, ref: "User", required: true },
type: { type: String, required: true },
tasks: [{ type: mongoose.Schema.Types.ObjectId, ref: "Type" }]
});
module.exports = mongoose.model("TaskList", taskListSchema);
我不必在这里使用 async await,我可以只链接 promise ,但我不知道如何以逻辑可读的方式链接 promise ,因为如果任务不存在我必须创建它.
最佳答案
await
只允许在异步函数中使用(前提是您使用的环境支持它)。 Await
仅适用于 async
函数,您的 await
位于非异步的回调内部 - 只有您的顶级函数是 async
.你错过了这里的关键字:
.then(doc => {
// Should be:
.then(async doc => {
这样你就可以告诉你的代码 doc
回调是异步函数。但是,由于您的环境中有 async/await
,整个 block 可能会重构为看起来像那样!
exports.tasklists_add_task = async (req, res, next) => {
const id = req.params.tasklistId;
try {
let task = await Task.findOne({ externalId: req.body.externalId })
.exec();
if (!task) {
task = new Task({
_id: new mongoose.Types.ObjectId(),
externalId: req.body.externalId,
name: req.body.name
});
await task.save();
}
const result = await tasklist.update({_id: id}, {$push: { tasks: tasks }}).select("-__v").exec();
} catch (err) {
// Error handling here
}
}
在大多数情况下,不需要混合使用 async/await
和 then
。将其视为处理 promise 并将 then/catch
隐藏在顺序可读代码后面的奇特方式。
我建议调整代码,使其看起来像所提供的解决方案(大量混合 Promises 和 Async/Await 被认为有点反模式)。
关于javascript - Mongoose 难以理解如何正确使用 promises/async await,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52777291/