Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to handle errors from multiple then in catch of javascript promises?

let p be a promise we can do

p
.then(f1)
.then(f2)
.then(f3)
.catch(f4)

now in catch, error can be thrown from any of f1,f2,f3 or even p rejected

now what should be the proper way to handle errors in f4(or in catch) , as errors thrown above can be of different types, Can multiple if else be avoided in f4 ?

like image 467
ashish singh Avatar asked Sep 11 '17 16:09

ashish singh


2 Answers

You can define you own custom error. For example :

function CustomError(errorText){
    this.error = errorText;
}

Modify your functions. Add catch block for each Promise returned from function:

function p(){
    return new Promise(function(resolve, reject){ 
            //Your functionality here
         })
          .catch(function(error){
             Promise.reject(new CustomError('f1')));
         })
}

And so on: f2, f3, f4

And your catch block will be:

.catch((err) => {
    if(err instanceof CustomError){
        HandleCustomError(err);
    } else {
        //Some another error is happen
    }
 })

And you custom error handler will be something like that:

function HandleCustomError(customError){
     switch(customError.error){
         case 'f1':
            //handle f1
            break;
         case 'f2':
            //handle f2
            break;
         ...
     }
}
like image 125
freethinker Avatar answered Sep 29 '22 02:09

freethinker


By catching error in the Promise that is rejected, you won't need to worry about the different types of error in the final catch block, and your code should become more readable (in the sense that it's easier to see that each catch block handles the appropriate rejection).

I also recommend, if it's possible in your case, to use async/await. Rejected promises are equivalent to thrown Errors in this syntax. Instead of using a lot of chained Promises, the logic of "each catch block in the right place" is more direct and should make bugs easier to be spotted.

try {
  const v1 = await f1();
} catch (err) {
  // Process err
}

try {
  const v2 = await f2(v1);
} catch (err) {
  // Process err
}
like image 42
Vítor Castelo Branco Avatar answered Sep 29 '22 02:09

Vítor Castelo Branco