JavaScript Output
Before you can build anything interesting, you need to see what your code is doing. JavaScript gives you four built-in ways to produce output: write to the developer console, inject into the page, replace the entire document, or pop up a dialog. Each has its place — and one of them you should almost never touch.
The Four Output Methods at a Glance
| Method | Where Output Goes | Common Use |
|---|---|---|
console.log(...) |
Browser DevTools console | Debugging — your everyday tool |
element.innerHTML = ... |
A specific HTML element | Updating UI dynamically |
document.write(...) |
Directly into the document stream | Legacy — avoid |
alert(...) |
A blocking pop-up dialog | Quick demos, blocking prompts |
1. console.log() — Your Daily Driver
console.log() writes to the browser’s DevTools console. It’s how every JavaScript developer debugs every day.
console.log("Hello!");
// Output: Hello!
const user = { name: "Ada", age: 36 };
console.log(user);
// Output: {name: "Ada", age: 36}
console.log("Sum:", 2 + 3);
// Output: Sum: 5
console.log("a", "b", "c");
// Output: a b c
Open DevTools with F12 (or Cmd+Option+I on Mac), click Console, and you’ll see the output.
Other console Methods
console.log is just one of many. Use the right one for the situation:
| Method | What It Does |
|---|---|
console.log() |
Standard message |
console.info() |
Same as log but tagged “info” |
console.warn() |
Yellow warning |
console.error() |
Red error with stack trace |
console.table() |
Renders arrays/objects as a table |
console.dir() |
Inspects an object’s properties |
console.group() / groupEnd() |
Collapsible nested logs |
console.time() / timeEnd() |
Measures elapsed time |
console.warn("Cache is empty");
console.error("Failed to fetch user");
console.table([
{ name: "Ada", age: 36 },
{ name: "Linus", age: 54 }
]);
// Renders as a neat table in DevTools
console.time("loop");
for (let i = 0; i < 1_000_000; i++) {}
console.timeEnd("loop");
// Output: loop: 4.231ms
Tip: Prefer console.warn() and console.error() over console.log() for non-normal events — DevTools lets you filter by level.
2. innerHTML — Update a Page Element
Real apps don’t print to the console for the user — they update the page. Pick an element by id and set its innerHTML (or, more safely, textContent):
<h1 id="greeting">Hello</h1>
<button id="btn">Say Hi</button>
<script defer>
document.getElementById("btn").addEventListener("click", () => {
document.getElementById("greeting").innerHTML = "Hi, friend!";
});
</script>
Click the button — the <h1> text updates. That’s how every dynamic web page works under the hood.
innerHTML vs textContent
const el = document.getElementById("greeting");
el.innerHTML = "<em>Welcome</em>"; // Parses as HTML — <em> becomes italic
el.textContent = "<em>Welcome</em>"; // Renders literally as text including the tags
innerHTML |
textContent |
|
|---|---|---|
| Parses HTML tags | ✅ Yes | ❌ No (literal text) |
| Risk of XSS attack | ⚠️ Yes if you insert user input | ✅ Safe |
| Faster | ❌ Slower (parses) | ✅ Faster |
| Use when | You need HTML | You want plain text |
Warning: Never set innerHTML from user-supplied data without sanitising it. An attacker can inject <script> tags or event handlers. Use textContent for any untrusted string.
3. document.write() — Legacy, Avoid It
document.write() writes directly into the document stream while the page is parsing.
document.write("<h1>Hello</h1>");
It looks harmless, but if called after the page has finished loading, it wipes the entire document:
<body>
<h1>My App</h1>
<button onclick="document.write('Oops')">Click me</button>
<!-- After clicking: the whole page is replaced with "Oops" -->
</body>
| Why You’ll See It | Why You Shouldn’t Use It |
|---|---|
| Old W3Schools tutorials | Wipes the document if called after load |
| Quick “first script” examples | Blocks parsing, hurts performance |
| Some ancient ad scripts | Modern browsers actively warn about it |
Warning: Browsers may block document.write() in deferred or async scripts entirely. Treat it as deprecated.
4. alert(), confirm(), prompt() — Dialog Boxes
These are quick-and-dirty pop-ups. They block the entire page until the user dismisses them.
alert("Saved!");
// Pops up "Saved!" with an OK button
const wantsToDelete = confirm("Are you sure?");
// Pops up Yes / No, returns boolean
const name = prompt("What's your name?", "Guest");
// Pops up a text input, returns string (or null if cancelled)
They’re useful for quick demos, learning, or 30-second prototypes. Real apps build proper modal dialogs instead.
| Pros | Cons | |
|---|---|---|
alert / confirm / prompt |
Zero setup, blocking | Ugly, can’t be styled, browser-specific UI |
| Custom modal | Fully styled, accessible, async | Requires HTML/CSS/JS |
Putting It All Together
<!DOCTYPE html>
<html>
<body>
<h1 id="output">Result will appear here</h1>
<button id="run">Run</button>
<script defer>
document.getElementById("run").addEventListener("click", () => {
const name = prompt("Your name?", "Ada"); // dialog
console.log("User entered:", name); // console
document.getElementById("output").textContent =
`Welcome, ${name}!`; // innerHTML/textContent
});
</script>
</body>
</html>
Three different output methods, used appropriately:
promptto grab inputconsole.logfor the developertextContentto update the visible page
When to Use Which
Need to debug? ───────────────────────▶ console.log / console.table
Updating the visible page? ───────────▶ textContent (safe) or innerHTML (when HTML needed)
Asking the user a quick question? ────▶ confirm / prompt (only for demos)
Writing into the document at parse? ──▶ Avoid document.write entirely
Best Practices Checklist
- ✅ Use
console.log(and friends) heavily while developing — they’re free - ✅ Use
textContentfor any user-supplied string - ✅ Use
innerHTMLonly when you control the HTML being inserted - ❌ Don’t ship
console.logto production noise — strip them at build time - ❌ Don’t use
document.writein 2026 - ❌ Don’t use
alertfor real user-facing flows — it’s blocking and ugly
Note: Most build tools (Vite, Webpack, esbuild) can strip console.log calls in production builds. You can leave them in your source and trust the toolchain.
What’s Next?
Now you can see what your code is doing. Time to learn the building blocks of JavaScript code itself — statements, the smallest unit of work the engine executes.