tjugg
tjugg

Reputation: 3357

Waiting for callback functions to finish before continuing

function main(cb) {

  getFirstData(function(ResultsForFirstQuery) {

    // Do something with ResultsForFirstQuery

    // Call getSecondData with param Id I get from ResultsForFirstQuery()
    getSecondData(function(ResultsForFirstQuery[0].Id)) {

      // Now here I need to do something with data data I get from getSeconData(),
      // But the program only calls this AFTER cb(result) in MAIN because of async?
      // How to make the program to wait for this function to finish?

    });

  });

  // THIS GETS CALLED BEFORE getSeconData() is finished
  // but I need to modify data i get from getSeconData before
  // calling this.
  cb(result);
}

funtion getFirstData(cb) {

  var rows;
  var sql = "sql magic here"

  /* Make Sql-query here and return results as rows in cb */

  cb(rows);

}

funtion getSecondData(id, cb) {

  var rows;
  var sql = "sql magic here"

  /* Make Sql-query here and return its results as rows in cb */

  cb(rows);

}

I tried to comment the code so that SO readers can understand the problem better. Function main(cb) is getting called from another file where I use its callback to send mail but I left it out of the code as i don't think its relevant. I also left out the code what the functions in the code block do because I think it's not relevant, but if anyone is interested they are for generating an XML-file from multiple database tables. This is also an node.js application.

The problem I have is that when I call getFirstData() and getSecondData() and get their results, the getSeconData() is not executed before getFirstData() ends and results from these two functions are generated. How can I modify this program to make it wait for getSeconData() to finish before continuing?

Upvotes: 2

Views: 6838

Answers (2)

Felix Kling
Felix Kling

Reputation: 817128

As mentioned in the comment, you need to call cb(result) in the callback of the second function.

function main(cb) {

  getFirstData(function(ResultsForFirstQuery) {
    getSecondData(ResultsForFirstQuery[0].Id, function(ResultsForSecondQuery) {
      // compute away...
      cb(result);
    });
  });

}

Upvotes: 2

SoluableNonagon
SoluableNonagon

Reputation: 11752

A good way to do this is via Promises.

var a = getFirstData(cb) {
    return new Promise( function( resolve, reject ){
         // your code here
         resolve( some data );
    });
}
var b = getSecondData(id, cb) {
    return new Promise( function( resolve, reject ){
         // your code here
         resolve( some data );
    });
}

Promise.all( a, b).then(function(){
    // once both promises resolve, continue
});

Upvotes: 1

Related Questions