Why in Node.js you need to do asynchronous operations

You may have wondered why so many functions in Node.js take a callback. Instead of returning results as the function return value, the “results” are delivered by calling the callback function at a later time. You are trying to wrap your head around why so many operations in Node.js are asynchronous.

It may seem counterintuitive at first, but there is a reason for having to do a lot of asynchronous operations.

Single thread executing JavaScript

In Node.js, there is only one thread executing JavaScript. The operating model is based on events - when something happens (an event) then run a specific block of code (the event handler). The block of code being executed takes up the whole thread until it returns control back. The next event cannot fire its listener until the previous listener has finished.

In a server application you have to do small and quick code blocks and then get out of the way for other requests to get their turn. The other requests obey to this same contract, and collaboratively they make single thread serve multiple requests.

Node.js processing interleaves
Node.js serves multiple requests by interleaving small blocks of JavaScript.
Figure from "Aargh, 100 new requests while still serving the first one!"

Callbacks allow making use of waiting time

Asynchronous operations setup the call and then return immediately without any results. The results are delivered at a later time by calling the provided callback. During the time between initiating the call and getting the results, other computations can take place. This allows the waiting time to be used to serve other requests.

Other requests are served by returning control back to one level up. This ends the current block of JavaScript execution and allows the next event handler to be executed. This way small blocks of JavaScript interleave and serve multiple requests concurrently.

There can be multiple outstanding operations such as file reads, HTTP requests, database queries in air at one point in time. But there is only ever one block of JavaScript code in execution. These code blocks can be callbacks, listener handlers or, initially, the startup user code. When an asynchronous operation completes, the callback is called immediately or, if the previous code block has not finished, queued up for execution.

Asynchronous operations allow one thread to serve multiple requests

Asynchronous operations allow Node.js to serve multiple requests efficiently. An asynchronous call is initiated, and a callback is provided that is to be called later when the results are in. Between initiating the call and firing of the callback, other computations can take place. The block of JavaScript that initiated the call returns control back one level up allowing other blocks to be executed during the waiting time.

Related articles

Node doesn't wait for your database call to finish?

Node doesn't wait for your database call to finish?

Learn how asynchronous calls work and make your app run as you intended. Get short email course on asynchronicity and two chapters from Finish Your Node App.