jason
jason

Reputation: 7164

How to wait for the complete execution of a loop Node.js

I have such a loop :

var someArray = [];

for(var i = 0; i < myArray.length; i++) {
    var tempArray = [];

    arangodb.query('somequery')
        .then(
            cursor => cursor.all()
        ).then(
            keys => tempArray  = keys,
            err => console.error('Failed to execute query:', err)
        ).then(function () {
            someArray.push.apply(someArray, tempArray);
        });
} 

I want to do other operations when all tempArrays are collected in someArray. But since Node.js is async, I don't know how to do it. Can you help me with that? Thanks in advance.

Upvotes: 0

Views: 674

Answers (3)

user2065736
user2065736

Reputation:

The only way to track if all your async operations are complete or not is to simply keep count of success callback triggers and failure callback triggers. Following should help you out.

let count = 0;

const checkCompletion = (curr, total) => {
    if (curr < total) {
        // Not all tasks finised
    } else {
        // All done
    }
};

for(var i = 0; i < myArray.length; i++) {
    var   tempArray = [];
    arangodb.query('somequery')
        .then(cursor => cursor.all())
        .then(keys => {
            // success
            count += 1;
            checkCompletion(count, myArray.length);
        }).catch(e => {
            // failure
            count += 1;
            checkCompletion(count, myArray.length);
        });

}

Upvotes: 1

marvel308
marvel308

Reputation: 10458

you need to use Promise.all()

var someArray = [];

function queryDB(){
    return arangodb.query('somequery')
        .then(
            cursor => cursor.all()).then(
            keys => tempArray  = keys,
            err => console.error('Failed to execute query:', err)
         ).catch(function(err){
            console.log('Failed');
         })
}
var promiseArray = [];
for(var i = 0; i < myArray.length; i++)
{
   promiseArray.push(queryDB());
} 

Promise.all(promiseArray).then(function(results){

    someArray = results.filter(result => !!result);
})

basically queryDB() would return a promise, you can do Promise.all() to wait for all promises to resolve and then you can access the result in result

Upvotes: 1

Jaromanda X
Jaromanda X

Reputation: 1

This will result in a flat array of keys from cursor.all()

any arangodb.query that fails will be ignored (still with console output though)

Promise.all(myArray.map(item => 
    arangodb.query('somequery')
    .then(cursor => cursor.all()))
    .catch(err => console.error('Failed to execute query:', err))
)
// remove rejections, which will be undefined
.then(results => results.filter(result => !!result))
// flatten the results
.then(results => [].concat(...results))
.then(results => {
    // do things with the array of results
})

Upvotes: 3

Related Questions