
Node.js Tutorial – Day 3: Node.js Event Loop Explained
Welcome back to our Node.js Tutorial series! In Day 1, we introduced Node.js, and in Day 2, we explored Node.js modules. Today, we’re diving into one of the most powerful concepts in Node.js Event Loop.
The Event Loop is what makes Node.js non-blocking, asynchronous, and super efficient. Understanding it is essential to mastering backend development with Node.js.
What is the Event Loop in Node.js?
In simple terms, the Event Loop is the mechanism that allows Node.js to handle multiple requests at the same time, even though it runs on a single thread.
Instead of waiting for one task to finish before starting another, Node.js places tasks into a queue and processes them asynchronously.
Think of it like this:
- You’re at a restaurant.
- The chef (Node.js single thread) prepares orders one by one.
- The waiter (Event Loop) takes new orders and delivers food as soon as it’s ready.
This is what makes Node.js perfect for building fast and scalable applications.
How the Event Loop Works
The Event Loop has several phases, and each phase handles a specific type of operation:
- Timers Phase → Executes callbacks from
setTimeout
andsetInterval
. - Pending Callbacks → Executes I/O callbacks that were deferred.
- Idle, Prepare → Internal use only.
- Poll Phase → Retrieves new I/O events and executes callbacks.
- Check Phase → Executes
setImmediate
callbacks. - Close Callbacks → Executes
close
event callbacks (likesocket.on('close')
).
Synchronous vs Asynchronous Code
To understand the Event Loop better, let’s compare:
Example 1: Synchronous
console.log("Task 1");
console.log("Task 2");
console.log("Task 3");
Output:
Task 1
Task 2
Task 3
The code runs line by line in order.
Example 2: Asynchronous
console.log("Task 1");
setTimeout(() => {
console.log("Task 2 (after 2 seconds)");
}, 2000);
console.log("Task 3");
Output:
Task 1
Task 3
Task 2 (after 2 seconds)
Here, the Event Loop executes Task 1
and Task 3
first, and when the timer finishes, it runs Task 2
.
EventEmitter in Node.js
Node.js uses an EventEmitter class to handle events. You can listen to and trigger custom events easily.
Example: Using EventEmitter
const EventEmitter = require('events');
const emitter = new EventEmitter();
// Listener
emitter.on('greet', (name) => {
console.log(`Hello, ${name}!`);
});
// Trigger Event
emitter.emit('greet', 'Node.js Tutorial Reader');
Output:
Hello, Node.js Tutorial Reader!
This is how Node.js manages real-time events like chat messages, notifications, or API calls.
Mini-Project: Event-Driven Logger
Let’s build a small event-driven logger using the Event Loop and EventEmitter.
logger.js
const EventEmitter = require('events');
const fs = require('fs');
class Logger extends EventEmitter {
log(message) {
this.emit('message', message);
}
}
const logger = new Logger();
logger.on('message', (msg) => {
fs.appendFileSync('log.txt', msg + '\n');
console.log("Logged:", msg);
});
module.exports = logger;
app.js
const logger = require('./logger');
logger.log("User logged in");
logger.log("File uploaded successfully");
logger.log("Error: Invalid request");
Output (log.txt):
User logged in
File uploaded successfully
Error: Invalid request
This mini-project shows how Node.js uses events and asynchronous behavior to handle tasks smoothly.
Why is the Event Loop Important?
- Handles multiple requests efficiently without creating new threads.
- Improves scalability – perfect for high-traffic applications.
- Powers real-time apps like chat apps, streaming platforms, and gaming servers.
For an official deep dive, check out the Node.js Event Loop Documentation.
Conclusion
In this lesson of our Node.js Tutorial, we explored:
- What the Event Loop is
- How it processes synchronous and asynchronous tasks
- The phases of the Event Loop
- Using
EventEmitter
for event-driven programming - A mini-project: Event-Driven Logger
The Event Loop is the backbone of Node.js, making it fast, efficient, and scalable.
👉 Up Next: Day 4 – Working with File System in Node.js