myTest532 myTest532
myTest532 myTest532

Reputation: 2381

Running async map in NodeJS

I'm trying to run async map in my NodeJS server, but it is not waiting the map to finish.

let test = `Start`;

    const array1 = ['A', 'B'];
    array1.map( async (arr1) => {
        test += ' ' + arr1;

        // Just a async request for testing. Return a name
        const pData = await property.getPropTotalUnitsByCompany(73);
        pData.map( (propData) => {
            test += ' ' + propData.PropertyName;
        });
    });

    console.log(test);

The console output is "Start A B". It never grab the data from property.getPropTotalUnitsByCompany.

getPropTotalUnitsByCompany returns an array with a couple of properties name. It looks like the code is not waiting to process the async request.

Upvotes: 1

Views: 142

Answers (2)

Alex Broadwin
Alex Broadwin

Reputation: 1338

You're right that, as written, that will not wait for the async functions to complete. You can have your async functions return a promise and then call Promise.all on the result of the map function, like so:

let test = `Start`;

const array1 = ['A', 'B'];

const promises = array1.map( async (arr1) => {
    test += ' ' + arr1;

    // Just a async request for testing. Return a name
    return property.getPropTotalUnitsByCompany(73).then(pData => {
        pData.map((propData) => {
            test += ' ' + propData.PropertyName;
        });
    });
});

await Promise.all(promises);

console.log(test);

Upvotes: 1

eol
eol

Reputation: 24555

Your assumption was correct, your code does not wait for the promises to resolve. Since your not really mapping something (you're not returing anything from your map and are rather pushing to the test variable), this can be simplified using a simple for .. of:

for (const element of array1) {
    test += ' ' + element;

    // Just a async request for testing. Return a name
    const pData = await property.getPropTotalUnitsByCompany(73);
    pData.forEach((propData) => {
        test += ' ' + propData.PropertyName;
    });
}

Here's a slightly adapted version of your code:

const someAsyncFunc = () => new Promise(resolve => setTimeout(() => resolve(["x", "y"]), 10));

(async () => {
    let test = `Start`;

    const array1 = ['A', 'B'];
    for (const element of array1) {
        test += ' ' + element;

        // Just a async request for testing. Return a name
        const pData = await someAsyncFunc();
        pData.forEach((propData) => {
            test += ' ' + propData;
        });
    }

    console.log(test); // prints "Start A x y B x y"
})()

Upvotes: 0

Related Questions