【问题标题】:Async await issue异步等待问题
【发布时间】:2021-10-11 15:34:21
【问题描述】:

在我的控制器模块中,我有一个函数 httpAddNewLaunch 在 POST 请求上调用:

async function httpAddNewLaunch(req, res) {
    let launch = req.body
    addNewLaunch(launch)
    console.log(launch)
    return res.status(201).json(launch)
}

AddNewLaunch 函数:

async function addNewLaunch(launch) {
    launch.flightNumber = (await launchesDataBase.findOne({})).flightNumber + 1
    console.log(launch)
    await saveLaunch(launch)
    // launches.set(launch.flightNumber, launch)
}

saveLaunch 函数:

async function saveLaunch(launch) {
   await launchesDataBase.findOneAndReplace({
        flightNumber: launch.flightNumber
    }, launch, {
        upsert: true
    })
}

当函数 httpAddNewLaunch 调用时,它不会等到它调用的其他函数完成(addNewLaunch(launch) -> saveLaunch(launch)),它只是继续执行,所以当我@987654324 @ 在调用 addNewLaunch(launch) 之后,它会记录一个没有 flightNumber 的对象。

然后我在 addNewLaunch(launch) 之前添加 await,它会附加 flightNumber。

如果异步函数只是返回 Promise 的函数,但它们像普通函数一样执行,那么为什么会这样工作,所以它们应该按调用顺序执行,但在我的情况下它不会等待并且只是没有 flightNumber 的 console.logs(launch)?

你能解释一下我哪里错了吗:)

【问题讨论】:

  • "只是返回 Promise 的函数,但它们像普通函数一样执行" - 除非它们 await 很明显。

标签: javascript node.js asynchronous mongoose promise


【解决方案1】:

我建议阅读 Promises 和 async/await 的工作原理。有很多很好的指南/解释,在开始使用它们之前您可能应该已经了解它们。

基本上,JS 函数是逐语句执行的。 await 关键字基本上把它放在了它的头上:你当前的函数调用将“暂停”,直到给定的 Promise 解决。 如果它拒绝,你的 await promise 将改为抛出。 这就是 async 函数的全部意义:能够在 await 实现另一个函数时“暂停函数调用”承诺。

【讨论】:

  • 我相信使用“暂停”这个词,即使加上引号,也可能会导致混淆。
  • 暂停?屈服?不确定哪个词最合适。
  • @KelvinSchoofs “暂停(执行)”在这里是正确的术语。 Yielding 是生成器函数所做的事情,尽管“yield”也可以用作“produce”的一般同义词(在迭代器、函数调用、表达式评估等中)。
  • 还有可能是错字:with -> will
【解决方案2】:

异步函数本质上返回一个承诺。因此,当您在没有等待的情况下调用 addNewLaunch(launch) 时,承诺会被解决/拒绝,但您不会等待响应。添加 await 以“等待”承诺结束。

await addNewLaunch(launch);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-12-09
    • 1970-01-01
    • 2022-10-25
    • 2019-03-27
    • 2022-01-25
    • 1970-01-01
    • 2020-10-16
    • 1970-01-01
    相关资源
    最近更新 更多