-1

I'm struggling with async await block. I have looked the multiple resources on the net but I just can't understand what I'm doing wrong here :

app.post('/api/my-api', async (req, res, next) => {
try {
    filecontent = req.files.userFile.data.toString('utf8')
    console.log("decoded file : ", filecontent);
    let encoded_file = new Buffer(filecontent).toString('base64');
    var apiClass = new RPC("http://localhost:1006", "my-api");

    //the asynchronous function :
    const answ = await apiMethod.call("api", [{"file" : encoded_file, "fileName":req.files.userFile.name}], res.json);

    //the code I'd like to execute only after the previous function has finished :
    console.log("answer : ", answ);
    console.log("answering...");
    res.json(answ);
} catch (err) {
    console.log(err);
}

Apparently my console.log are executed before the the await line is done. I can tell because there's a console.log() in the asynchronous function too, and my res.json is sent before I receive answ.

How do I make sure the asynchronous function finishes before the rest of the code ?

Edit : here is the apiMethod.call function :

call(id, params) {
    let options = {
        url: this.url,
        method: "post",
        headers:
        { 
         "content-type": "text/plain"
        },
        body: JSON.stringify( {"jsonrpc": "2.0", "id": id, "method": this.procedure, "params": params })
    };
    console.log(options);
    request(options, (error, response, body) => {
        if (error) {
            console.error('An error has occurred: ', error);
        } else {
            console.log('Post successful: response: ', body);
        }
    });
}
anis
  • 3
  • 4
  • Can `app.post` be `await`ed ? – Alex Feb 12 '21 at 08:25
  • What does `apiMethod.call` return? – Thomas Sablik Feb 12 '21 at 08:28
  • Looks like that your apiMethod.call does not return a Promise. What is the value of ```answ``` in your ```console.log("answer : ", answ)``` ? – Mike Malyi Feb 12 '21 at 08:29
  • well, it's answ is "undefined". answ is supposed to be the answer from the call to an API. So if I have to make it return a promise, how do I also get the answer from the API ? – anis Feb 12 '21 at 08:36
  • @anis — We have no idea how `apiMethod` works, so it’s *really* hard to suggest how it could be changed to work differently. – Quentin Feb 12 '21 at 08:46
  • Please provide a [mcve]. If `apiMethod.call` doesn't return anything you can't await it. Does it expect a callback? _"So if I have to make it return a promise, how do I also get the answer from the API ?"_ The promise contains the answer. – Thomas Sablik Feb 12 '21 at 08:48
  • I added the .call() function too – anis Feb 12 '21 at 09:12

1 Answers1

1

Issue is in call function. Since it has async code (request call), it should be wrapped in promise which should resolve from callback function of request.

Updating call function to something like below should help:

function call(id, params) {
  return new Promise((resolve, reject) => {
    let options = {
      url: this.url,
      method: "post",
      headers: {
        "content-type": "text/plain",
      },
      body: JSON.stringify({
        jsonrpc: "2.0",
        id: id,
        method: this.procedure,
        params: params,
      }),
    };
    console.log(options);
    request(options, (error, response, body) => {
      if (error) {
        console.error("An error has occurred: ", error);
        reject(error);
      } else {
        console.log("Post successful: response: ", body);
        resolve(body);
      }
    });
  })
}

Raeesaa
  • 3,267
  • 2
  • 22
  • 44