Promises - error callback vs. catch
Asked Answered
C

2

20

Can somebody tell me if there is a difference between using an error callback vs. a catch function, when using $q.promise please?

E.g. are the two snippets of code functionally equivalent?

function doSomething0() {
    var deferred = $q.defer();

    ...

    return deferred.promise;
 }

 doSomething0()
    .then(doSomething1)
    .then(doSomething2)
    .then(doSomething3)
    .catch(function (err) {
        // do something with `err`
    });

vs.

function doSomething0() {
    var deferred = $q.defer();

    ...

    return deferred.promise;
 }

 function errorHandler(err) {
    // do something with `err`
 }

 doSomething0()
    .then(doSomething1, errorHandler)
    .then(doSomething2, errorHandler)
    .then(doSomething3, errorHandler);

If so, why use the second one? It looks far uglier and leads to more code duplication in my opinion?

Caruso answered 23/9, 2015 at 16:41 Comment(3)
The second version allows you to bring the promise back into a resolved state to continue with the chain anyway by returning anything other than an error or a rejected promise.Burmaburman
And if the error handler throws or returns a rejected promise, it will be called three times.Uprise
I think errorHandler will be called three times only if doSomething3 fails. But if doSomething2 fails, it will be called two times and if doSomething1 fails, it will be called once.Onepiece
D
6

Both will achieve the same thing, except the second one might run errorHandler three times (instead of just once). You are correct that it brings some code duplication, but it also allows you to treat whatever error happened and continue with your chain:

function errorHandler(err) {
  //log error, continue
  return $q.resolve('default value or something');
}

doSomething0()
  .then(doSomething1, errorHandler)
  .then(doSomething2, errorHandler)
  .then(doSomething3, errorHandler);
Demythologize answered 23/9, 2015 at 16:48 Comment(4)
Thank you! How would I continue with the chain out of interest? Or will it just continue with the chain?Caruso
@Caruso you just have to return a new Promise from your error handler function, just like in the example above!Demythologize
No need to return a promise. You can simply return a value.Uprise
"Both will achieve the same thing". Not exactly. See this please: https://mcmap.net/q/626204/-promises-error-callback-vs-catchSchell
S
2

Let's have a look at the first sample:

doSomething0()
    .then(doSomething1, errorHandler)
    .then(doSomething2, errorHandler)
    .then(doSomething3, errorHandler);


// I've represented functions invocations as if they were synchronous to simplify the example to focus on the error handling
// The above sample is in a way "equivalent" to
try {
    // doSomething0()
    try {
        // doSomething1()
        try {
          // doSomething2()
        } catch(e0) {
           // handle error
        }  
    } catch(e1) {
         // handle error
    }
} catch(e2) {
     // handle error
}
// doSomething3()

But if an exception happens in the doSomething3 handler, it won't be handled.

Ok, let's have a look at the second sample:

doSomething0()
    .then(doSomething1)
    .then(doSomething2)
    .then(doSomething3)
    .catch(function (err) {
        // do something with `err`
    });


// I've represented functions invocations as if they were synchronous to simplify the example to focus on the error handling
// The above sample is in a way "equivalent" to
try {
    // doSomething0()
    // doSomething1()
    // doSomething2()
    // doSomething3()
}
catch(e) {
    // Catch 'em all
    console.log(e)
}
Schell answered 3/12, 2020 at 16:26 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.