Asynchronous JavaScript

JavaScript is single-threaded. The event loop lets it handle slow tasks (timers, network requests) without blocking.

Call stackmain()console.log()Web APIssetTimeout · fetchDOM eventsasync callMicrotask queue — promise callbacks (run first)Task queue — timers, eventscallback readyEvent loop
JavaScript event loop
JavaScript
console.log("1");
setTimeout(() => console.log("2 (timer)"), 0);
Promise.resolve().then(() => console.log("3 (microtask)"));
console.log("4");
1 4 3 (microtask) 2 (timer)
Why this order?Synchronous code runs first, then microtasks (promises), then macrotasks (timers).

Promises

JavaScript
function getMarks(roll) {
    return new Promise((resolve, reject) => {
        setTimeout(() => {
            roll > 0 ? resolve({ roll, marks: 88 }) : reject("Invalid roll number");
        }, 500);
    });
}

getMarks(7)
    .then(data => console.log("Got:", data.marks))
    .catch(err => console.log("Error:", err))
    .finally(() => console.log("Done"));
Got: 88 Done

async / await

JavaScript
async function showUser() {
    try {
        const res = await fetch("https://jsonplaceholder.typicode.com/users/1");
        if (!res.ok) throw new Error("HTTP " + res.status);
        const user = await res.json();
        console.log(user.name);
    } catch (err) {
        console.log("Failed:", err.message);
    }
}
showUser();
Leanne Graham

Run several promises at once with Promise.all([...]) (fails if any fails) or Promise.allSettled([...]) (waits for all and reports each result).

Track your progress through the JavaScript course