JavaScript Promise

JavaScript Promise

In this tutorial, you will learn about JavaScript promises, what are promises and how to use them.

Imagine that you have a car(🚗) shop. Where cars (🚗🚗🚗) are repaired.

And a customer (💁) brings his car (🚗) to your repair shop. And says that my car has to be repaired. It has some problems.

Promise you that your car (🚗) will be repaired till evening today. Here you promise the customer. But three states are formed in it. Given below states of promise:

  • When the car(🚗) came to your repair center, it was in the pending state.
  • If you repair the car(🚗) till today evening. So your promise is resolved.
  • If the problem of the car(🚗) is not solved today evening, then it comes to the reject state.

Let us now explain to you the promises of JavaScript.

Understanding Promises in JavaScript

In JavaScript, a promise is an object that contains the future value of an asynchronous operation.

Sometimes, when you work with webservers and requesting some data from a webserver, the javascript promise promises us to get data from webserver and you can use in the future.

States of a Promise

javascript promises states

A promise has three states:

  • Pending: first of all, the job is in a pending state.
  • Fulfilled: A Promise is resolved if the job finished successfully.
  • Rejected: A Promise is rejected if the job an error occurred.

Note that, A promise begins in the pending state which indicates that the promise hasn’t completed. It finishes with either a successful or failed state.

Creating a Promise

You can see the following syntax for how to create promises using Promise constructor.

The constructor syntax for a promise object is:

let promise = new Promise((resolve, reject) => {     ...   });

To create a promise in JavaScript, you use the Promise constructor, new Promise  the executor and it runs automatically. It contains the producing code which should eventually produce the result.

The promise is resolved by calling the resolve() and rejected by calling reject().

See the following example:

let finish = true;

let res = new Promise(function (resolve, reject) {
    if (finish) {
        resolve("Your 🚗 has repaired.");
    } else {
        reject("Your 🚗 has not repaired yet.");
    }
});

The Promise constructor takes a function as an argument and this function takes two functions resolve() and reject()

When you call the new Promise(executor), the executor is called automatically. 

According to job state, inside the executor(new promise), you can call resolve() and reject() function, if completed job successfully then call resolve()  and if job failed then reject().

See the following example:

let finish = true;

let res = new Promise(function (resolve, reject) {
    setTimeout(() => {
        if (finish) {
            resolve("Your 🚗 has repaired.");
        } else {
            reject("Your 🚗 has not repaired yet.");
        }
    }, 5 * 1000);
});
console.log(res);

Now, you see that the promise begins with the pending state with the value is undefined. The promise value will be returned later once the promise is fulfilled.

After the 5 seconds timer finishes, the promise is either resolved or rejected randomly, and its value will be the value passed to the resolve or reject function. See the following:

That was an example of a job resolved.

After that, If you change the value of the finish variable and it value to false and run the script again:

let finish = false;

Note that, this time Calling reject() state and display error message after 5 seconds.

That was an example of a job rejected.

When you create a Promise object using new Promise , this time is in pending state until it is not fulfilled state (resolved or rejected).

Consuming a Promise

You can consume promise by calling then(), catch() and , finally() methods on the promise.

1) The then() method

The Then is called when a promise is resolved. 

See the following syntax to represent then() method:

promiseObject.then(onFulfilled, onRejected);

Note that, it takes two parameters:

  • The onFulfilled callback is called if the promise is fulfilled.
  • The onRejected callback is called when the promise is rejected.

The following function returns a Promise object:

function doPromise(finish) {
    return new Promise(function (resolve, reject) {
        setTimeout(() => {
            if (finish) {
                resolve("Your 🚗 has repaired.");
            } else {
                reject("Your 🚗 has not repaired yet.");
            }
        }, 4 * 1000);
    });
}

And the following calls the doPromise() function and invokes the then() method:

let res = doPromise(true);

res.then(
    success => console.log(success),
    reason => console.log(reason)
);

2) The catch() method

The catch is called when a promise is rejected. 

res.catch(
    reason => console.log(reason)
);

Internally, the catch() method invokes the then(undefined, onRejected) method.

3) The finally() method

In every situtation want to execute the same piece of code whether the promise is resolved or rejected.

You can see the following example:

function carRepair() {
    // ...
}

res
    .then(
        (success) => {
            console.log(success);
            carRepair();
        }
    ).catch(
        (reason) => {
            console.log(reason);
            carRepair();
        }
    );

As you can see, the carRepair() function call is duplicated in both then() and catch() methods.

To remove this duplicate and execute the carRepair() whether the promise is fulfilled or rejected, you use the finally() method, like this:

res
    .then(success => console.log(success))
    .catch(reason => console.log(reason))
    .finally(() => carRepair());

JavaScript Promise Example

In this example, we will show you how to load google news headlines from google webserver using json api.

Suppose that we have the following JSON file: https://newsapi.org/v2/top-headlines?country=us&apiKey=e03753c9126b408d870a44318813ac3d

When you call this google news api, you will looks like:

{
   "status":"ok",
   "totalResults":38,
   "articles":[
      {
        {
         "source":{
            "id":"fox-news",
            "name":"Fox News"
         },
         "author":"Daniel Canova",
         "title":"Phil Mickelson teases big plans for 'The Match,' suggests Michael Jordan, Tony Romo, others could participate - Fox News",
         "description":"There’s no doubt about it that “The Match: Champions for Charity” lived up to the hype.",
         "url":"https://www.foxnews.com/sports/phil-mickelson-big-plans-the-match-michael-jordan-tony-romo",
         "urlToImage":"https://static.foxnews.com/foxnews.com/content/uploads/2020/05/The-Match-Champions-for-Charity-2.jpg",
         "publishedAt":"2020-05-27T22:48:22Z",
         "content":"There’s no doubt about it that “The Match: Champions for Charity” lived up to the hype.\r\nThe charity golf match featuring legends Tiger Woods, Phil Mickelson, Tom Brady and Peyton Manning raised $20 … [+2453 chars]"
      }
      }
   ]
}

The following shows the HTML page that contains a google news button. When you click the google news button, the page loads data from the google news webserver and display latest news headines:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title>JavaScript Promise Demo</title>
</head>
<body>
    <div id="container">
        <button id="btnGet">Get News</button><br>
        <div id="news"> </div>
    </div>
    <script src="">
    </script>
</body>
</html>

To load google news headlines from google news webserver, we’ll use the XMLHttpRequest object. Later, you will learn how to use the fetch() method.

The following function returns a Promise object that loads data from a remote file:

function load(url) {
    return new Promise(function (resolve, reject) {
        const request = new XMLHttpRequest();

        request.onreadystatechange = function (e) {
            if (this.readyState === 4) {
                if (this.status == 200) {
                    resolve(this.response);
                } else {
                    reject(this.status);
                }
            }
        }
        request.open('GET', url, true);
        request.responseType = 'json';
        request.send();
    });
}

Inside the new promise, call resolve() function and passed in the response if the HTTP status code is 200, otherwise, we invoked the reject() function and passed in the HTTP status code.

Register the button click event listener and call the then() method on the Promise. If the load is successful, then show google news headlines from the google news web server. Otherwise, we show the error message with the HTTP status code.

const btn = document.querySelector('#btnGet');
const msg = document.querySelector('#news');
btn.onclick = function () {
    load('https://newsapi.org/v2/top-headlines?country=us&amp;apiKey=e03753c9126b408d870a44318813ac3d')
        .then(function(data) {
       
        for (i = 0; i < data.articles.length; i++) {
              var node = document.createElement("LI");
              var textnode = document.createTextNode(data.articles[i].title);
              node.appendChild(textnode);
              document.getElementById("news").appendChild(node);
        }
       
    });
}

See the following output, when you call this api using js promise:

Conclusion

In this tutorial you have learned the following:

  • A promise is an object that returns a value in the future.
  • How to create a promise in javascript.
  • How to call promise with differents states.
  • A promise begins in the pending state and finishes in either fulfilled state or rejected state.
  • The then is called when a promise is resolved. 
  • The catch is called when a promise is rejected. 
  • finally() method execute piece of code, whether the promise is resolved or rejected.
  • Call google news api and display news headlines using the js promises

AuthorTuts Make

My name is Devendra Dode. I am a full-stack developer, entrepreneur, and owner of Tutsmake.com. I like writing tutorials and tips that can help other developers. I share tutorials of PHP, Javascript, JQuery, Laravel, Livewire, Codeigniter, Vue JS, Angular JS, React Js, WordPress, and Bootstrap from a starting stage. As well as demo example.

Leave a Reply

Your email address will not be published. Required fields are marked *