The event loop drains the entire microtask queue before running the next macrotask. A promise .then() is a microtask, while setTimeout schedules a macrotask. Even with a 0ms delay, the timer callback waits until all microtasks (and synchronous code) have finished, so "promise" always beats "timeout".