【问题标题】:How to await a callback function call in Node.js?如何在 Node.js 中等待回调函数调用?
【发布时间】:2021-06-03 04:36:21
【问题描述】:

我是 Node.js 和 Javascript 的新手,我使用 npm package retry 向服务器发送请求。

const retry = require('retry');

async function HandleReq() {

//Some code
return await SendReqToServer();
}

async function SendReqToServer() {
 
operation.attempt(async (currentAttempt) =>{
        try {
            let resp = await axios.post("http://localhost:5000/api/", data, options);
            return resp.data;
        } catch (e) {
            if(operation.retry(e)) {throw e;}
        }
    });
}

我得到空响应,因为 SendReqToServer 在传递给 operation.attempt 的函数解析承诺之前返回了一个承诺。

如何解决这个问题?

【问题讨论】:

  • SendReqToServer 不返回任何内容,这是故意的吗?
  • return resp.data 将数据返回给.attempt 回调。您需要返回 operation.attempt(...) 以将值返回到 SendReqToServer
  • @evolutionxbox SendReqToServer 返回一个承诺。
  • @ThomasSablik 是的,但在调用 operation.attempt() 后它会立即解决 - 实际上不需要等待任何东西 - 因为函数末尾基本上有一个隐含的 return undefined;
  • @ThomasSablik 确实如此。 - OP:SendReqToServer 解析为 undefined,我认为这不是故意的

标签: javascript node.js asynchronous async-await callback


【解决方案1】:

这个问题的答案取决于operation.attempt。如果它返回一个承诺,您也可以简单地在SendReqToServer 中返回该承诺。但通常带有回调的异步函数不会返回承诺。创建你自己的承诺:

const retry = require('retry');

async function HandleReq() {

//Some code
return await SendReqToServer();
}

async function SendReqToServer() {
 
    return new Promise((resolve, reject) => {
        operation.attempt(async (currentAttempt) => {
            try {
                let resp = await axios.post("http://localhost:5000/api/", data, options);
                resolve(resp.data);
                return resp.data;
            } catch (e) {
                if(operation.retry(e)) {throw e;}
            }
        });
    });
}

【讨论】:

  • 非常感谢,这可行,但发生上述问题是因为传递的回调函数等待axios's 承诺解决,但operation.attempt's 没有,我的理解是否正确?跨度>
  • @AjaySabarish 没错。 operation.attempt 被调用,它几乎立即完成。回调异步运行。
  • 谢谢,但是你说如果operation.attempt返回一个promise,我们可以这样返回它,但是我们怎么能确定这个promise会包含它的回调promise中返回的值呢?
  • @AjaySabarish 你必须阅读文档或源代码才能看到它实际返回的内容。
  • 哦,好的,明白了,谢谢,但不一定总是正确的,即使operation.attempt 返回一个承诺?
【解决方案2】:

返回operation.attempt() 将返回resp.data如果函数中没有错误sendReqToServer()。 目前,您只是将resp.data 返回到operation.attempt()。您还需要返回operation.attempt()

const retry = require('retry');

async function HandleReq() {

//Some code
return SendReqToServer();
}

async function SendReqToServer() {
 
return operation.attempt(async (currentAttempt) => {
        try {
            let resp = await axios.post("http://localhost:5000/api/", data, options);
            return resp.data;
        } catch (e) {
            if(operation.retry(e)) {throw e;}
        }
    });
}

【讨论】:

  • 如果operation.attempt 没有返回承诺怎么办?这行不通。
  • 非常感谢您的回复。 operation.attempt 不返回承诺
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-08-12
  • 2017-07-28
  • 2016-02-17
  • 2011-06-27
  • 2020-09-29
相关资源
最近更新 更多