A JavaScript Promise is an object that can be used to get the outcome of an asynchronous operation when that result is not instantly available.

Since JavaScript code runs in a non-blocking manner, promises become essential when we have to wait for some asynchronous operation without holding back the execution of the rest of the code. Some common use cases for promises include using data from APIs and downloading images.

Promise object state

Promises are ideal for performing asynchronous JavaScript operations. This is supported by their use of three states:

  • A pending state, where the promise has yet to resolve or be rejected.
  • A fulfilled status, where asynchronous operations are complete and a value has been returned.
  • A rejected state, where asynchronous operations have failed at some point.


A Promise object is returned from a function that accepts two unique functions: resolve and reject:

let myPromise = new Promise((resolve, reject) => {
// Promise code here

If myPromise yields a legitimate value, it will execute the resolve() function. However, if something were to go awry, such as bad data or a server error, the reject() function would execute, instead.


Chaining is a technique used to perform additional operations against a “fulfilled” promise. The following methods are used for promise chaining:

  • .then(), which performs operations on a fulfilled promise object and returns a new value.
  • .catch(), which handles any anticipated promise rejections and throws an error.
  • .finally(), which executes without regard to whether the promise was fulfilled or rejected.

Below is a brief example of using chaining to produce a success message after the promise is fulfilled:

const promise = new Promise((resolve, reject) => {
const term1 = 2;
const term2 = 2;
const expression = term1 + term2;
const answer = 4;
const expressionIsCorrect = expression === answer;
// 2 + 2 = 4, and 4 = 4, so this is true!
if (expressionIsCorrect) {
resolve('The promise was fulfilled!');
} else {
errorType: 'ArithmeticError',
message: "The expression didn't evaluate correctly.",
originalExpression: `${term1} + ${term2} === ${answer}`,
.then((message) => {
console.log(`Success: ${message}`);
.catch((err) => {
`${err.errorType}: ${err.message} \nOriginal Expression: ${err.originalExpression}`
.finally((message) => {
console.log('Operations finished');
// Output: Success: The promise was fulfilled!


Returns a new Promise that can be accessed as an array of resolved values of fulfulled Promises. It takes an iterable object, such as an Array, that contains one or more Promise objects. This is ideal when working with Promises that depend on one another's completion.
Returns a new Promise object that resolves to an array after all Promises in iterableObject have been resolved or rejected. This is ideal when working with multiple Promises that are independent of one another's completion. Each element in the resolved array will be the result of the Promises in iterableObject.
Iterates over an iterableObject of Promises and stops at the first one that fulfills. The resulting value from that fulfilled Promise is resolved in the returned Promise object.
Returns a new Promise related to a previously rejected Promise in the chain. This is ideal for formatting error messages for potential Promise rejections.
Returns a new Promise object after the previous Promise in the chain has been resolved or rejected. This last part of the chain will execute no matter what.
Returns the first Promise in an iterableObject that is either resolved or rejected.
Returns a rejected Promise object with a given reason.
Returns a new Promise object that turns into the value that was passed to the method.
Returns a new Promise object.
Interested in helping build Docs? Read the Contribution Guide or share your feedback.

Learn JavaScript on Codecademy