JavaScript Promises: A Journey from Callbacks to Custom Implementation

JavaScript Promises: A Journey from Callbacks to Custom Implementation

How Life Was Before Promises?

Before the introduction of promises in JavaScript, handling asynchronous operations was a cumbersome and error-prone process. Developers relied heavily on callbacks, which often led to "callback hell" or "pyramid of doom," where nested callbacks became difficult to manage and read. This made the code harder to maintain and debug, especially as the complexity of the application grew.

For example, consider the following scenario: You need to perform three asynchronous operations sequentially. In the callback-based approach, you'd end up nesting the functions, leading to deeply indented code that's difficult to follow.

This pattern not only makes the code harder to read but also complicates error handling since each callback needs to manage its own errors.

Why does the concept of Promises Come to JavaScript?

Promises were introduced in JavaScript to solve the problems associated with callback-based asynchronous programming. A promise represents a value that may be available now, or in the future, or never. It allows you to chain asynchronous operations in a more readable and maintainable way, avoiding deeply nested callbacks.

Promises provide a clean way to handle asynchronous tasks, making the code easier to write, read, and maintain. They also offer a unified approach to error handling, allowing errors to be caught at a single point in the chain.

How Promises Made Life Easier: An Example

With promises, the previous example can be rewritten as follows:

In this example, the code is linear and easy to follow. Each then block handles the result of the previous operation, and the catch block handles any errors that occur during any of the asynchronous operations.

How Promises Use Callbacks Under the Hood

Despite their clean syntax, promises are essentially a wrapper around callbacks. When you create a promise, you pass an executor function to it, which receives two arguments: resolve and reject. These functions are callbacks that the promise uses to transition from a pending state to either a fulfilled or rejected state.

Under the hood, promises manage the state and the callback queue. When a promise is fulfilled or rejected, it processes the queued callbacks and passes the resolved value or error to them.

Implementation of JavaScript Promises

Here's a custom implementation of JavaScript promises using a class named Promise2. This implementation illustrates how promises manage state, handle callbacks, and provide a chainable interface.

Usage Example

This implementation demonstrates the basics of how promises work in JavaScript. The Promise2 the class manages the state of the promise, queues callbacks, and processes them when the promise is fulfilled or rejected.

Implementing the Fetch function using Promise2

The fetch function is a modern JavaScript API for making HTTP requests. It is used to request resources from a network server and handle responses.

In the implementation of fetch2, we require a library for making HTTP requests and the fetch function returns a Promise2 object that is in a pending state until the request is either rejected or fulfilled.

Fetch2 usage example

This concludes the article, where we explored the concept of promises, examined how they function internally, and gained insights into how fetch operates under the hood.

I've also published this article on Hashnode, which offers better code visibility and the ability to easily copy code snippets. [ Click Here To Read ]

Rajesh kisan Sambakwad

Swami Ramanand teerth Marathwada University Nanded

3mo

Very informative

Like
Reply
Vaibhav Srivastava

AI ML Enthusiast <Generative AI>

3mo

**Insight**: JavaScript promises streamline handling asynchronous operations by providing a clear structure with three states (pending, fulfilled, rejected) and methods for managing success and failure. They improve code readability and maintainability compared to nested callbacks. Custom implementations, like `Promise2`, illustrate the core mechanics of promises, including state management and handler execution, highlighting how promises simplify async programming.

Like
Reply
Vaibhav Srivastava

AI ML Enthusiast <Generative AI>

3mo

### Summary of JavaScript Promises 1. **Callback Hell**: Managing async operations with nested callbacks can lead to messy, hard-to-maintain code. 2. **Promises**: Introduced to simplify async operations. They represent a value that will be available in the future and help avoid callback hell. 3. **Promise States**: - **Pending**: Initial state. - **Fulfilled**: Operation succeeded. - **Rejected**: Operation failed. 4. **Handlers**: - **`.then(onFulfilled, onRejected)`**: Registers callbacks for success and failure. 5. **Custom Implementation**: A simple promise (e.g., `Promise2`) tracks state, manages fulfillment and rejection, and queues handlers for when the promise settles. Promises make async code cleaner and more manageable by allowing chaining and easier error handling.

Like
Reply
Ekansh Saxena

SDE @Expedia Group | Siemens Scholar - Batch 07 | ICPC Regionalist '21

4mo

Insightful

Alok Yadav

Frontend Engineer @crio.do | Javascript |React| Technical Content Writer

4mo

Very informative ✨

To view or add a comment, sign in

Insights from the community

Others also viewed

Explore topics