Build fluency in the vocabulary of a single thread continuously pulling the next task off a queue.
0 / 5 completed
1 / 5
At standup, a dev mentions a single thread continuously pulling the next task off a queue, whether it's a timer firing, an I/O callback, or a promise resolving, and running it to completion before picking up the next one. What is this mechanism called?
The event loop is a single thread continuously pulling the next task off a queue, whether that's a timer callback, an I/O completion, or a resolved promise's continuation, and running it to completion before moving on to the next one. A thread pool instead relies on multiple reusable worker threads running tasks in parallel, which is a fundamentally different concurrency model. This single-threaded, one-task-at-a-time loop is what makes an event-loop-based runtime like Node.js or a browser's JavaScript engine handle high I/O concurrency without needing multiple threads.
2 / 5
During a design review, the team distinguishes microtasks, like a resolved promise's callback, from macrotasks, like a timer or an I/O event, and confirms all pending microtasks drain completely before the loop moves to the next macrotask. Which capability does this ordering guarantee?
This ordering guarantees promise continuations running as soon as possible after the current task finishes, ahead of the next timer or I/O callback, since the event loop drains the entire microtask queue completely before it's allowed to move on to the next macrotask. If continuations instead ran strictly after every pending timer and I/O event, a chain of resolved promises could be starved indefinitely by a steady stream of macrotasks. This microtask-before-macrotask rule is a foundational part of how a modern JavaScript runtime schedules asynchronous work predictably.
3 / 5
In a code review, a dev notices a synchronous loop performing a large in-memory computation that takes several seconds, with no yielding back to the event loop in between. What does this represent?
This is blocking the event loop, since a single-threaded event loop can only run one task at a time, so a long synchronous computation with no yielding point prevents any other queued callback, including something as basic as handling a user click, from running until that computation finally finishes. A memory leak is an unrelated concept about memory never being released. This blocking behavior is exactly why CPU-heavy work is typically moved off the main event-loop thread, whether to a worker thread or a separate process, rather than run inline.
4 / 5
An incident report shows a web application became completely unresponsive to user input for several seconds during a bulk data transformation, because the transformation ran as one long synchronous function with no chance for the event loop to process other queued callbacks in between. What practice would prevent this?
Breaking the transformation into smaller chunks that yield back to the event loop between them, or moving the entire computation to a separate worker thread, lets other queued callbacks, including user input handling, keep running instead of being frozen out for the whole duration. Continuing to run it as one long unyielding synchronous function is exactly what caused the multi-second unresponsiveness in this incident. This chunking or offloading is the standard fix for any CPU-heavy task that would otherwise monopolize a single-threaded event loop.
5 / 5
During a PR review, a teammate asks why the team moves CPU-heavy work off the main event loop into a worker thread instead of just running it inline and trusting it to finish quickly enough. What is the reasoning?
The event loop is single-threaded, so any long-running synchronous task, no matter how quick it seems in testing, blocks every other queued callback until it completes, and that blocking window grows directly with the size of whatever data is being processed. Offloading that work to a worker thread keeps the main loop entirely free to keep handling other events, timers, and I/O concurrently while the heavy computation runs elsewhere. The tradeoff is the added complexity of communicating results back from the worker thread, typically through message passing rather than shared memory.