Путаница вокруг «вложенных» операторов try / catch в Javascript - PullRequest
0 голосов
/ 19 апреля 2020

По сути, у меня есть асинхронная c функция, содержащая try / catch, которая вызывает другую асинхронную c функцию, также содержащую try catch, и я немного запутался, как правильно реализовать то, что я делаю. Какой-то «псевдокод», показывающий мою текущую реализацию:

const main = async () => {
  try {
    const test = await secondFunc();
    console.log(test);

  } catch(err) {

    console.log('Found an error!');
    console.log(err);
  }

const secondFunc = async () => {
  try {
    await performSomeRequestExample();

  } catch(err) {
    if (err.x === 'x') {
      doSomething();
    } else {

      //********
      throw err;
      //********
  }

}

Итак, я пытаюсь сделать так, чтобы throw(err) (окруженный звездочками) был пойман catch в main() который также вызовет console.log('Found an error!'), но в настоящее время происходит ошибка из secondFunc(), catch в main() никогда не срабатывает, и я получаю необработанное отклонение обещания.

Любое руководство на что я делаю не так?

Ответы [ 4 ]

1 голос
/ 19 апреля 2020

Мой совет - минимизировать использование try / catch, если в этом нет крайней необходимости. С async функциями (или любыми функциями, которые возвращают объект Promise) вы обычно можете упростить вещи, не беспокоясь о блоках try / catch, если вам не нужно делать что-то определенное c с определенными ошибками. Вы также можете использовать .catch вместо блоков try / catch, чтобы упростить чтение.

Например, приведенный выше код может быть написан так:

const main = async () => {
  const test = await secondFunc().catch(err => {
    console.log("Found an error from secondFunc!", err);
    throw err;  // if you want to send it along to main's caller
  });
  if (test) {
    console.log("Test", test);
  }
};

const secondFunc = () => {
  return performSomeRequestExample().catch(err => {
    if (err.x === "x") {
      doSomething();
    } else {
      throw err;
    }
  });
};

const performSomeRequestExample = () => Promise.reject("bad");

main().then(
  () => console.log("worked"),
  err => console.log("failed from main", err)
);

В secondFunc нам не нужно использовать async, поскольку мы можем просто вернуть обещание, возвращаемое из performSomeRequestExample, и обработать любые сбои в .catch.

0 голосов
/ 19 апреля 2020

Другое решение может быть таким:

const main =  async() => {
try {
    const test = await secondFunc();
    console.log(test);

  } catch(err) {

    console.log('Found an error!');
    console.log(err);
  }
}

const secondFunc = async () => {
  //return await performSomeRequestExample();  //for success
  return await performSomeRequestExample(2); //for error
}

const performSomeRequestExample = async(abc=1) => {
  return new Promise(function(resolve,reject){
    if(abc ==1){
      setInterval(resolve("yes"),400);
    }else{
      setInterval(reject("opps"),400);
    }
  });
}


main();

Проверьте этот код по этой ссылке: https://repl.it/repls/JoyfulSomberTelevision

0 голосов
/ 19 апреля 2020

Добавьте возврат перед ожиданием executeSomeRequestExample.

const secondFunc = async () => {
    try {
        return await performSomeRequestExample();
    } catch (err) {
        if (err.x === 'x') {
            console.log('x');
        } else {
            throw err;
        }
    }
}

или вы также можете использовать .catch () после ожидаемой функции.

0 голосов
/ 19 апреля 2020

Вы должны использовать

const secondFunc = async () => {
  performSomeRequestExample().then(res =>{
    console.log(res);
  })
  .catch(err => {
    console.log(err);
  }
)
...