Thursday, October 29, 2015

JavaScript Promises

In today's blog post we will discuss what promises are in JavaScript and how they are useful. In my last week's blog post here, I discussed about callback functions and the callback hell problem. Today, we will see how promises can help us tackle the callback hell problem.

Promise

Promise represents the eventual result of an asynchronous operation. Promise is an object which represents a handle that listens to the results of an async operation. In other words, Promise promises to alert you when async operation is done and return the results.



Promises in JavaScript


As we know, in the nested callbacks, it's really difficult to manage and debug the code and it gets worse with more nesting. For example, if you have something like this:

function load(){
  var connection = new connection();
  connection.loadBook(function(err, connection){
      connection.loadChapter(function(err, connection){
          connection.loadPages(err, function(err, collection){
          });
      });
  }); 
}

You can see this is getting ugly and will be difficult to manage. Now, on top of it, if you add error handling to each and every call, the function may look something like this:

function load(){
   var connection = new connection();
   try
   {
       connection.loadBook(function(err, connection) 
       {
           try
           {
               connection.loadChapter(function
                    (err, connection) 
               {
                   try
                   {
                     connection.loadPages(err, 
                 function(err, collection) 
                       {
                       });
                   }
                   catch(ex)
                   {
                       //handle exception for load chapter
                   }
               });
           }
           catch(ex)
           {
               //handle exception for load chapter
           }
       });
   } 
   catch(ex)
   {
       //handle exception for load book
   } 
}


You can see the point, it's even more ugly and difficult to manage. This is called callback hell problem.

Promises

Promises are used to solve the callback hell problem. Promises are part of libraries like jquery, Q, RSVP and are also part of ES6. Let's understand the basics first.

A promise has 3 different states:
i)   PENDING       - not done yet
ii)  FULFILLED   - done
iii) REJECTED     - error
There is also a 4th stage i.e. SETTLED which means that promise is either Fulfilled or Rejected. 

When we create a promise, we need to pass in 2 different methods:
i)  resolve - method that's called on successful completion of promise
ii) reject   -  method that's called on error


var promise = new Promise(function(resolve, reject) {
  if (1==1) {   //we can decide any condition here
    resolve("Promise worked!");
  }
  else {
    reject(Error("Promise failed"));
  }
});
promise.then(function(result) {
  console.log(result); 
}, function(err) {
  console.log(err); 
});

When we invoke the promise using "then", we pass in the functions that need to be used for resolve and reject.

So the example code we saw with callback hell problem above, might look something like this with promises:

function load()
{
    var connection = new connection();
    connection.getbook().then(function(book){
       return getChapter(book.id);
    }).then(function(chapter){
       return getPages(chapter.id); 
    }).then(undefined, function(error){
       //handle error
    })
}

As you can see the code looks so much better with promises. The error handling has been simplified too. The last "then" in the code above uses only reject function, so we passed undefined for resolve function there and only reject function has the value.

Conclusion

Promises help us write asynchronous code in a much cleaner and efficient way. As asynchronous code is becoming more and more prevalent, promises are being used more often.

For future updates to my weekly blog, please subscribe to my blog via the "Subscribe To Weekly Post" feature at the right and follow me on Twitter. Until then Happy Coding :)


No comments:

Post a Comment