Event Loop
Event loop = JavaScript's async mechanism
What is the Event Loop?
"Single thread + async callbacks"
The event loop is JavaScript's mechanism for handling asynchronous operations in a single-threaded environment.
"The event loop is JavaScript's concurrency model that enables asynchronous operations despite being single-threaded, using a call stack, callback queue, and event loop."
JavaScript Runtime Components
Call Stack · Web APIs · Callback Queue · Event Loop
┌─────────────┐
│ Call Stack │ ← Synchronous code
└─────────────┘
↓
┌─────────────┐
│ Web APIs │ ← setTimeout, fetch, DOM
└─────────────┘
↓
┌─────────────┐
│ Callback │ ← Ready callbacks
│ Queue │
└─────────────┘
↓
┌─────────────┐
│ Event Loop │ ← Moves callbacks to stack
└─────────────┘
"The event loop coordinates the call stack, Web APIs, and callback queue to handle asynchronous operations."
How It Works
Stack → APIs → Queue → Loop
- Call Stack: Executes synchronous code
- Web APIs: Handle async operations (setTimeout, fetch)
- Callback Queue: Holds ready callbacks
- Event Loop: Moves callbacks from queue to stack when stack is empty
"The event loop continuously checks if the call stack is empty, then moves callbacks from the queue to the stack."
Example Flow
Synchronous first, async later
console.log("1");
setTimeout(() => console.log("2"), 0);
Promise.resolve().then(() => console.log("3"));
console.log("4");
// Output: 1, 4, 3, 2
Why?
1and4are synchronous3is microtask (Promise)2is macrotask (setTimeout)
"Synchronous code runs first, then microtasks (Promises), then macrotasks (setTimeout)."
Microtasks vs Macrotasks
Microtasks > Macrotasks
| Type | Examples | Priority |
|---|---|---|
| Microtasks | Promises, queueMicrotask | High |
| Macrotasks | setTimeout, setInterval | Low |
"Microtasks (Promises) have higher priority than macrotasks (setTimeout) in the event loop."
Call Stack
LIFO - Last In, First Out
- Executes code synchronously
- One function at a time
- Blocks when busy
- Stack overflow if too deep
"The call stack executes code synchronously in a LIFO manner, blocking when processing."
Blocking the Event Loop
Heavy computation blocks everything
// ❌ Blocks event loop
for (let i = 0; i < 1000000000; i++) {
// heavy computation
}
// ✅ Use Web Workers or break up work
"Heavy synchronous operations block the event loop, preventing other code from running."
setTimeout(0)
Defer to next event loop cycle
console.log("1");
setTimeout(() => console.log("2"), 0);
console.log("3");
// Output: 1, 3, 2
Even with 0ms delay, setTimeout runs after current execution.
"setTimeout with 0ms defers execution to the next event loop cycle, after current code completes."
9️⃣ Promise Queue
Promises = microtask queue
Promise.resolve().then(() => console.log("microtask"));
setTimeout(() => console.log("macrotask"), 0);
// microtask runs first
"Promises are added to the microtask queue, which has priority over the macrotask queue."
Visual Example
Order matters
console.log("Start");
setTimeout(() => console.log("Timeout"), 0);
Promise.resolve()
.then(() => console.log("Promise 1"))
.then(() => console.log("Promise 2"));
console.log("End");
// Output: Start, End, Promise 1, Promise 2, Timeout
"The event loop enables asynchronous JavaScript in a single-threaded environment. It uses a call stack for synchronous code, Web APIs for async operations, and callback queues. The event loop moves callbacks from queues to the stack when the stack is empty. Microtasks (Promises) have higher priority than macrotasks (setTimeout). Synchronous code always runs first, then microtasks, then macrotasks."
🧠 Ultra-Short Cheat Sheet
Single-threaded
Call stack (synchronous)
Web APIs (async)
Callback queue
Event loop (coordinator)
Microtasks > Macrotasks
Synchronous first