search
HomeWeb Front-endJS TutorialInversion of Control in JavaScript Callbacks: Why Promises are the Answer

A callback function is a function passed into another function as an argument, which is then invoked inside the outer function to complete some kind of routine or action. There are two ways in which the callback may be called: synchronous and asynchronous. It is the most fundamental async pattern in Javascript.

For example:

Inversion of Control in JavaScript Callbacks: Why Promises are the Answer

A and B happen now, under the direct control of the main JS program. But C gets deferred to happen later, and under the control of another party, in this case, the ajax(..) function. In a basic sense, that sort of hand-off of control doesn’t regularly cause lots of problems for programs.

However, infrequency is not sufficient to ignore the problem or issue. In fact, it’s one of the major problems of callback-driven design. It revolves around the idea that sometimes ajax(..) or the “party” you pass your callback continuation to is not a function that you wrote, or that you directly control. Many times it’s a utility provided by some third party.

We call this “inversion of control” when you take part of your program and give over control of its execution to another third party. There’s an unspoken “contract” that exists between your code and the third-party utility — a set of things you expect to be maintained.

What is the problem with “Inversion of Control”?

There is an example for better understanding this problem.

Let’s say you’re building a travel booking website for your company. You’ve added a “book now” button that uses a third-party library’s createBooking() function. This function processes the booking and then calls your callback to send a confirmation email to the customer.

This code might look like:

Inversion of Control in JavaScript Callbacks: Why Promises are the Answer

Everything works perfectly during testing. People start booking travel packages on your website, and everyone is happy with your work. Suddenly, one day, you get a call from your boss regarding a major issue. A customer booked a package and received four identical confirmation emails for one booking.

You start debugging the issue. You review the part of the code that sends the confirmation email, and everything seems correct. You then investigate further and find that the createBooking() utility from the third-party library called your callback function four times, resulting in four confirmation emails being sent.

You contact the third-party library’s support team and explain the situation. They tell you they have never encountered this issue before but will prioritize it and get back to you. After a day, they call you back with their findings. They discovered that an experimental piece of code, which was not supposed to go live, had caused the createBooking() function to call the callback multiple times.

The issue was on their side, and they assured you that it has been fixed. They apologized for the trouble and confirmed that the problem would not occur again.

To prevent any unwanted issue like that after some seeking for a solution, you implement a simple if statement like the following, which the team seems happy with:

Inversion of Control in JavaScript Callbacks: Why Promises are the Answer

But then one of the QA engineers asks, “what happens if they never call the callback?” Oops. Neither of you had thought about that!

You start to think of all the possible things that could go wrong with them calling your callback. Here is a list of some of the problems:

  • Call the callback too early

  • Call the callback too late (or never)

  • Call the callback too few or too many times (like the problem in the example above)

  • Swallow any errors/exceptions that may happen

  • ...

You will probably realize that you have to implement many solutions in your code for different situations, which will make the code awful and dirty because it is required in every single callback passed to a utility.

Promises

What if we could uninvert that inversion of control? What if instead of passing the continuation of our program to another party, we could expect it to return us a capability to know when its task finishes, and then our code could decide what to do next?

Promises offer a powerful way to handle asynchronous operations in JavaScript, addressing issues like callback hell and inversion of control. Unlike callbacks, Promises lets you manage asynchronous tasks without giving up control of your code.

Consider ordering a cheeseburger at a fast-food restaurant. You receive a receipt, a promise of your future cheeseburger. While you wait, you can do other things, knowing you’ll get your order eventually. Similarly, a Promise in JavaScript represents a future value, allowing your code to proceed smoothly.

Promises also handle failures gracefully, just as you might be informed if the restaurant runs out of cheeseburgers. This structure makes your code more readable and maintainable.

I’m not going to go in depth into Promises here, but by using them, you can write cleaner, more reliable asynchronous code, improving the overall quality of your JavaScript applications.

For example, for the travel booking website we described earlier, if the third-party utility returns a promise we can handle it like this:

Inversion of Control in JavaScript Callbacks: Why Promises are the Answer

Once a Promise is resolved (successfully completed), it stays that way forever — it becomes an immutable value at that point and can then be observed as many times as necessary. That means a resolved promise, its resolved value can be accessed or used multiple times in your code without affecting its state. This allows you to handle the result of the asynchronous operation in various parts of your application without worrying about the Promise changing or being re-evaluated.

Promises are a solution for the inversion of control issues that occur in callback-only code. Callbacks represent an inversion of control. So inverting the callback pattern is actually an inversion of inversion, or an uninversion of control. Restoring control back to the calling code where we wanted it to be in the first place.

References

  • You Don’t Know JS: Async & Performance by Kyle Simpson

  • developer.mozilla.org

The above is the detailed content of Inversion of Control in JavaScript Callbacks: Why Promises are the Answer. For more information, please follow other related articles on the PHP Chinese website!

Statement
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn
Replace String Characters in JavaScriptReplace String Characters in JavaScriptMar 11, 2025 am 12:07 AM

Detailed explanation of JavaScript string replacement method and FAQ This article will explore two ways to replace string characters in JavaScript: internal JavaScript code and internal HTML for web pages. Replace string inside JavaScript code The most direct way is to use the replace() method: str = str.replace("find","replace"); This method replaces only the first match. To replace all matches, use a regular expression and add the global flag g: str = str.replace(/fi

How do I create and publish my own JavaScript libraries?How do I create and publish my own JavaScript libraries?Mar 18, 2025 pm 03:12 PM

Article discusses creating, publishing, and maintaining JavaScript libraries, focusing on planning, development, testing, documentation, and promotion strategies.

How do I optimize JavaScript code for performance in the browser?How do I optimize JavaScript code for performance in the browser?Mar 18, 2025 pm 03:14 PM

The article discusses strategies for optimizing JavaScript performance in browsers, focusing on reducing execution time and minimizing impact on page load speed.

How do I debug JavaScript code effectively using browser developer tools?How do I debug JavaScript code effectively using browser developer tools?Mar 18, 2025 pm 03:16 PM

The article discusses effective JavaScript debugging using browser developer tools, focusing on setting breakpoints, using the console, and analyzing performance.

jQuery Matrix EffectsjQuery Matrix EffectsMar 10, 2025 am 12:52 AM

Bring matrix movie effects to your page! This is a cool jQuery plugin based on the famous movie "The Matrix". The plugin simulates the classic green character effects in the movie, and just select a picture and the plugin will convert it into a matrix-style picture filled with numeric characters. Come and try it, it's very interesting! How it works The plugin loads the image onto the canvas and reads the pixel and color values: data = ctx.getImageData(x, y, settings.grainSize, settings.grainSize).data The plugin cleverly reads the rectangular area of ​​the picture and uses jQuery to calculate the average color of each area. Then, use

How to Build a Simple jQuery SliderHow to Build a Simple jQuery SliderMar 11, 2025 am 12:19 AM

This article will guide you to create a simple picture carousel using the jQuery library. We will use the bxSlider library, which is built on jQuery and provides many configuration options to set up the carousel. Nowadays, picture carousel has become a must-have feature on the website - one picture is better than a thousand words! After deciding to use the picture carousel, the next question is how to create it. First, you need to collect high-quality, high-resolution pictures. Next, you need to create a picture carousel using HTML and some JavaScript code. There are many libraries on the web that can help you create carousels in different ways. We will use the open source bxSlider library. The bxSlider library supports responsive design, so the carousel built with this library can be adapted to any

How to Upload and Download CSV Files With AngularHow to Upload and Download CSV Files With AngularMar 10, 2025 am 01:01 AM

Data sets are extremely essential in building API models and various business processes. This is why importing and exporting CSV is an often-needed functionality.In this tutorial, you will learn how to download and import a CSV file within an Angular

Enhancing Structural Markup with JavaScriptEnhancing Structural Markup with JavaScriptMar 10, 2025 am 12:18 AM

Key Points Enhanced structured tagging with JavaScript can significantly improve the accessibility and maintainability of web page content while reducing file size. JavaScript can be effectively used to dynamically add functionality to HTML elements, such as using the cite attribute to automatically insert reference links into block references. Integrating JavaScript with structured tags allows you to create dynamic user interfaces, such as tab panels that do not require page refresh. It is crucial to ensure that JavaScript enhancements do not hinder the basic functionality of web pages; even if JavaScript is disabled, the page should remain functional. Advanced JavaScript technology can be used (

See all articles

Hot AI Tools

Undresser.AI Undress

Undresser.AI Undress

AI-powered app for creating realistic nude photos

AI Clothes Remover

AI Clothes Remover

Online AI tool for removing clothes from photos.

Undress AI Tool

Undress AI Tool

Undress images for free

Clothoff.io

Clothoff.io

AI clothes remover

AI Hentai Generator

AI Hentai Generator

Generate AI Hentai for free.

Hot Article

R.E.P.O. Energy Crystals Explained and What They Do (Yellow Crystal)
3 weeks agoBy尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. Best Graphic Settings
3 weeks agoBy尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. How to Fix Audio if You Can't Hear Anyone
3 weeks agoBy尊渡假赌尊渡假赌尊渡假赌

Hot Tools

VSCode Windows 64-bit Download

VSCode Windows 64-bit Download

A free and powerful IDE editor launched by Microsoft

SublimeText3 Mac version

SublimeText3 Mac version

God-level code editing software (SublimeText3)

MantisBT

MantisBT

Mantis is an easy-to-deploy web-based defect tracking tool designed to aid in product defect tracking. It requires PHP, MySQL and a web server. Check out our demo and hosting services.

Notepad++7.3.1

Notepad++7.3.1

Easy-to-use and free code editor

SAP NetWeaver Server Adapter for Eclipse

SAP NetWeaver Server Adapter for Eclipse

Integrate Eclipse with SAP NetWeaver application server.