Benson OO
Benson OO

Reputation: 517

whats wrong with my promise,async/await function both are returning empty arrays

i have an array of objects in my code which is shown below

[ { name: 'JMCP', priority: 1 },
  { name: 'OTC', priority: 2 },
  { name: 'CMT', priority: 3 },
  { name: 'SMPP', priority: 4 },
  { name: 'CDRBilling', priority: 5 },
  { name: 'Colgate', priority: 6 },
  { name: 'FFM', priority: 7 },
  { name: 'PBX', priority: 8 },
  { name: 'BeepCall', priority: 9 },
  { name: 'MWIFI', priority: 10 },
  { name: 'PoolData', priority: 11 } ]

what i want to do is update each objects name and priority property in my mongodb database which is working fine the issue i am facing is when i try to store names of each object within an array its always empty below given is my code

 async function abc(arrofObjects)
 {
 var new_prod=new Array();
 arrofObjects.forEach(async (ele)=>{
 await ProductsModel.update({name:ele.name}, {"$set":{"priority": ele.priority}});
 // Up till Here everything is working fine all records are being updated accordingly
 // the issue arises here
 new_prod.push(ele.name); 
 })
 console.log(new_prod); //Here its always empty
 return new_prod;
 }

I tried doing it through promises either but all in vain...

getFinalArr(arrofObjects).then(console.log)// logs empty array
getFinalArr(arr){
  var finalArr=new Array();
  return new Promise((resolve)=>{
  arr.forEach(async (item)=>{
  await ProductsModel.update({name:item.name}, {"$set":{"priority": item.priority}});
   // Up till Here everything is working fine all records are being updated accordingly
  // the issue arises here
  await finalArr.push(await item.name);
});
console.log(finalArr);//always empty
resolve(finalArr);
})
}

Upvotes: 0

Views: 79

Answers (2)

Jason
Jason

Reputation: 3179

You can also perform asynchronous functions with for of

for (let ele of arrofObjects) {
    await ProductsModel.update({name:item.name}, {"$set":{"priority": item.priority}});
    // Up till Here everything is working fine all records are being updated accordingly
    finalArr.push(item.name);
}

The limitation of this solution is that the update() calls will all be made sequentially, which may be slower than you are hoping for. But it also has the advantage that not all of the requests will fire at once, swamping the server.

If the list is small enough that fan-out won't kill you, I'd map() it to an array of promises, then await the results:

let promises = arrofObjects.map((ele) => ProductsModel.update(...));
let new_prod = await Promise.all(promises);

Of course it always starts small and then creeps up when you're busy looking at something else...

Upvotes: 0

user8246956
user8246956

Reputation:

The forEach() is asynchronous, so new_prod will be returned before being filled.

You should try the following:

async function abc(arrofObjects)
{
 var new_prod=new Array();
 for (var index = 0; index < arrofObjects.length; index++) {
    var ele = arrofObjects[index];
    await ProductsModel.update({name:ele.name}, {"$set":{"priority": ele.priority}});
    new_prod.push(ele.name);
 }
 console.log(new_prod);
 return new_prod;
}

Upvotes: 1

Related Questions