JavaScript error handling async function passed to reduce

I'm passing an async function to an array reduce function. What's the syntax for catching errors thrown by the passed in function? The reducing is happening inside a try catch block, which is catching other errors just fine, but node gives me an UnhandledPromiseRejectionWarning if the passed in function itself throws an error.

Code:

aFunction = async (anArray) => {
  try {
    const result = await anArray.reduce(async (a, b) => {
      await doSomethingTo(b);
    }, Promise.resolve());

    return result;
  }

  catch (error) {
    winston.error(error);
  }  
}

(Edit) Actual code:

exports.chainedQueryDB = async (queries, finalTask, download) => {
  let client = await pool.connect();
  try {
    winston.info(`Begin chained table query.`);
    // Loop through query array
    const result = await queries.reduce(async (a, b) => {
      await client.query(b);
    }, Promise.resolve());

    if (download) {
      return streamOut(download, client);
    }

    return result.rows;
  }

  catch (error) {
    throw error;
  }

  finally {
    const final = await client.query(finalTask);
    winston.info(`Temp table dropped.`);
    client.release();
  }
}

(Edit) Report: Replacing await client.query(b) with await a; return client.query(b); await a; return client.query(b); solved the problem. With just await client.query(b) , reduce seemed to 1) generate a bunch of floating client.query calls that all ran even if an earlier promise was rejected, and 2) caused an unhandled promise rejection warning. Using await a; return client.query(b); await a; return client.query(b); stops execution on first rejection and the catch block catches the error as originally intended.


You need to do something with the promise in the accumulator (the a parameter) as well - await it, handle its errors by installing a .catch() callback, wait for it concurrently with the doSomething(b) . For a sequential execution, you could do

async function aFunction(anArray) {
  try {
    return await anArray.reduce(async (a, b) => {
      await a; // make sure the previous query is done
      return doSomethingTo(b);
    }, Promise.resolve());
  } catch (error) {
    winston.error(error);
  }
}

I would hover recommend to simply not use reduce here:

async function aFunction(anArray) {
  try {
    let result;
    for (const b of anArray) {
      result = await doSomethingTo(b);
    }
    return result;
  } catch (error) {
    winston.error(error);
  }
}

To avoid the UnhandledPromiseRejectionWarning you can chain .catch() to aFunction() call or utilizing second parameter of .then() to handle the rejected Promise or error.

Alternatively, chain .catch() to doSomethingTo(b) call to handle the error.

链接地址: http://www.djcxy.com/p/26624.html

上一篇: 检查一个对象是否有属性

下一篇: JavaScript错误处理异步函数传递给reduce