Can You Answer This Senior Level JavaScript Promise Interview Question?

 

Can You Answer This Senior Level JavaScript Promise Interview Question?


Most interviewees failed on it.


What is the output of the following code?

const promise = new Promise((resolve, reject) => {
console.log(1);
setTimeout(() => {
console.log("timerStart");
resolve("success");
console.log("timerEnd");
}, 0);
console.log(2);
});

promise.then((res) => {
console.log(res);
});

console.log(4);

Execution Process:

Synchronous Code Execution:

  • The interpreter begins execution with synchronous tasks.
  • It first logs 1 to the console.
  • It hits the setTimeout() but only registers it in the Macro Task Queue since it's an asynchronous function.
  • It logs 2 (continuing synchronous execution).

promise.then() Registration:

  • Although promise.then() is called, it does not execute immediately.
  • The .then callback is registered in the Micro Task Queue, which takes priority over the Macro Task Queue.

Final Synchronous Execution:

  • console.log(4) executes since it’s synchronous.

Event Loop Execution (Micro and Macro Tasks):

  • The synchronous call stack is now empty, so the event loop begins processing queued tasks.
  • Micro Tasks are processed first:
  • The promise.then() callback executes and logs the resolve value ("success") to the console.
  • Macro Tasks (like setTimeout) run after all Micro Tasks:
  • The callback inside setTimeout() logs "timerStart" and "timerEnd".

Final Output (In Order):

1
2
4
timerStart
timerEnd
success

In JavaScript:

  1. Synchronous Code always executes first, line by line, as part of the main call stack.
  2. Promises (.then()) are Micro Tasks, and they get higher priority over tasks registered using setTimeout or setInterval (known as Macro Tasks).
  3. The Event Loop manages the execution order:
  • It processes the Call Stack (synchronous tasks).
  • Next, it handles Micro Tasks (e.g., Promise.then()).
  • Finally, Macro Tasks (setTimeout callbacks) are executed.

In the above code:

  • 1 and 2 log synchronously.
  • console.log(4) logs immediately after registering the asynchronous tasks.
  • The promise’s .then() resolves before setTimeout's callback because Micro Tasks take priority.

This distinction between Micro Tasks and Macro Tasks is crucial for understanding JavaScript’s concurrency model


Conclusion

Understanding the difference between synchronous code, micro tasks, and macro tasks is crucial for mastering JavaScript’s event loop. Here’s a concise takeaway:

Synchronous Code executes first, blocking other tasks.

Promises (.then) are part of the Micro Task Queue, which has a higher priority than the Macro Task Queue (e.g., setTimeout).

The Event Loop processes:

  • First: Synchronous code (main call stack).
  • Next: Micro tasks.
  • Finally: Macro tasks.

In the provided example, the combination of synchronous logging, promise resolution, and the setTimeout callback highlights how tasks are ordered and executed. Understanding this behavior allows you to optimize code performance and avoid common pitfalls in asynchronous programming.

By mastering these concepts, you’ll gain better control over asynchronous tasks, ensuring your code runs smoothly and efficiently.

Comments