JavaScript BOM
BOM gives your JavaScript access to browser features like URL control, history, and local storage. It is essential when building real web app behavior beyond page content.
The BOM (Browser Object Model) refers to browser-provided APIs that let JavaScript interact with the browser environment beyond the page's DOM content. It gives you access to things like the URL, screen size, browser history, and storage.
The BOM is not part of the JavaScript language standard,
but modern browsers provide these APIs consistently. Many
commonly used browser APIs are exposed through properties and
methods of the global window object.
Why does the BOM matter?
- Redirect users or read the current URL with
window.location. - Navigate browser history programmatically with
window.history. - Read browser and device information with
window.navigator. - Read display information with
window.screen. - Store data in the browser with
localStorageandsessionStorage. - Show dialogs, set timers, and control the viewport through the
windowobject itself.
BOM hierarchy
Many commonly used browser APIs are exposed through properties and methods of the global window object:
-
window - represents the current browsing context and provides access to many browser APIs
- window.history - the session navigation history
- window.navigator - browser and device information
- window.screen - information about the display
- window.location - current URL and navigation
- window.localStorage - persistent key-value storage
- window.sessionStorage - tab-scoped key-value storage
How these APIs work together
A real browser feature usually combines several BOM tools. For example, a weather page can read a city from location.search, use navigator.onLine to decide whether to show an offline message, save the last city in localStorage, and use history.pushState() when the user selects a new city. The APIs are separate tools, but they work together around one user task.
const params = new URLSearchParams(location.search);
const city = params.get("city") || localStorage.getItem("lastCity") || "London";
if (!navigator.onLine) {
console.log("You are offline. Showing the last saved city:", city);
}
localStorage.setItem("lastCity", city);
history.pushState({ city }, "", `?city=${encodeURIComponent(city)}`);
In a normal browser page, window is the global object for classic scripts, so you can omit it when calling many of its properties. Writing location.href is the same as writing window.location.href. In a classic script, a top-level var declaration becomes a window property, but top-level let and const declarations do not. ES modules have their own module scope.
// The window object is the global object for classic browser scripts
console.log(window); // shows all browser properties and methods
// A top-level var becomes a property of window
var appTitle = "TaskManager";
console.log(window.appTitle); // Output: TaskManager
In a browser, window represents the current
browsing context and provides access to many browser APIs.
It is the global object for classic scripts running in a
normal browser page. Common properties and methods include innerWidth,
innerHeight, alert(),
confirm(), setTimeout(), and
setInterval().
// Viewport size
console.log(window.innerWidth); // e.g. 1440
console.log(window.innerHeight); // e.g. 900
// Open a popup
window.alert("Hello!");
// Run code after a delay (milliseconds)
window.setTimeout(function () {
console.log("1 second later");
}, 1000);
// Run code repeatedly
const id = window.setInterval(function () {
console.log("every 2 seconds");
}, 2000);
// Stop the interval
window.clearInterval(id);
window.history gives access to the
browser's session history, which is the list of pages
the user has visited in the current tab. You can navigate
back and forward without a page reload.
// Go back one page (same as clicking the Back button)
history.back();
// Go forward one page
history.forward();
// Go a specific number of steps (-2 = two pages back)
history.go(-2);
// Total number of entries in the history stack
console.log(history.length);
Changing the URL without reloading: pushState adds a new entry to the history stack and changes the address bar. replaceState changes the current entry instead, so it does not add another Back-button step. Neither method downloads a new page by itself.
| Method | What changes | Does it add a history entry? |
|---|---|---|
history.back() or forward() |
Moves to an existing entry. | No |
history.pushState(data, "", url) |
Updates the URL and stores optional state data. | Yes |
history.replaceState(data, "", url) |
Updates the current URL and state data. | No, it replaces the current entry |
popstate event |
Lets code respond when the user moves through state entries with Back or Forward. | It reacts to navigation; it does not create an entry |
// Adds /products to the current page's history
history.pushState({ page: "products" }, "", "/products");
// Changes the current entry without adding another Back-button step
history.replaceState({ page: "products" }, "", "/products?sort=price");
// Back and Forward can trigger this event in a single-page app
window.addEventListener("popstate", (event) => {
const page = event.state?.page || "home";
console.log("Render the page for:", page);
});
SPA use case: a single-page app can show a different view, such as Home or Products, while keeping the same document loaded. Each link calls pushState; the popstate listener renders the view again when the user clicks the browser Back or Forward button.
const app = document.querySelector("#app");
function render(page) {
app.textContent = page === "products" ? "Products view" : "Home view";
}
function navigate(page) {
history.pushState({ page }, "", `/${page}`);
render(page);
}
document.querySelector("#products-link").addEventListener("click", (event) => {
event.preventDefault();
navigate("products");
});
window.addEventListener("popstate", (event) => {
render(event.state?.page || "home");
});
render(history.state?.page || "home");
In a real app, the link and #app element would be part of the HTML. The important pattern is: update the URL with pushState, render the selected view, and listen for popstate so browser navigation stays synchronized.
pushState does not make the server serve a new file. A deployed SPA also needs server fallback configuration so a direct visit to a route such as /products can load the app.
window.screen provides information about the
user's display, with dimensions reported in CSS pixels. This is different from the
browser viewport size (window.innerWidth), and
both values can change with display settings or device
pixel ratio.
// Full screen resolution
console.log(screen.width); // e.g. 1920
console.log(screen.height); // e.g. 1080
// Available area (excluding OS taskbar)
console.log(screen.availWidth);
console.log(screen.availHeight);
// Color depth in bits
console.log(screen.colorDepth); // e.g. 24
window.location holds the current page URL
and lets you navigate to a new URL from JavaScript.
Use URL or URLSearchParams when you
need to read query parameters instead of manually
splitting location.search.
// Full URL
console.log(location.href);
// e.g. "https://example.com/page?q=hello#section"
// Just the domain
console.log(location.hostname); // e.g. "example.com"
// Path after the domain
console.log(location.pathname); // e.g. "/page"
// Query string
console.log(location.search); // e.g. "?q=hello"
// Hash fragment
console.log(location.hash); // e.g. "#section"
// Navigate to a new page
location.href = "https://example.com";
// Reload the current page
location.reload();
localStorage lets you store key-value pairs
in the browser with no built-in expiry. Data usually
stays after the tab or browser is closed, but users or
browser policies can clear it. Storage is per origin,
stores strings only, and its quota varies by browser.
// Save a value
localStorage.setItem("theme", "dark");
// Read a value
const theme = localStorage.getItem("theme");
console.log(theme); // Output: dark
// Remove one item
localStorage.removeItem("theme");
// Clear everything
localStorage.clear();
// Storing objects (must convert to JSON string)
const preferences = { theme: "dark", fontSize: 16 };
localStorage.setItem("preferences", JSON.stringify(preferences));
// Reading back an object
const stored = JSON.parse(localStorage.getItem("preferences"));
console.log(stored.theme); // Output: dark
sessionStorage works like
localStorage, but data belongs to the
current origin and browsing tab. It is normally cleared
when that tab is closed, so it is useful for temporary
data that should not persist between browser sessions.
// Save a value for the session
sessionStorage.setItem("step", "2");
// Read the value
console.log(sessionStorage.getItem("step")); // Output: 2
// Remove it
sessionStorage.removeItem("step");
// Data is normally cleared when the tab closes
Key difference: localStorage data persists
until the user, browser, or application clears it,
while
sessionStorage data is normally cleared when
the tab is closed.
Browser APIs are powerful because they can remember data, navigate users, and expose device information. Treat anything stored or received in the browser as potentially visible to the user and to scripts running in the page.
- Never store passwords, private keys, or long-lived authentication tokens in
localStorageorsessionStorage. XSS can read them. - Do not put secrets in URLs. Query strings can appear in browser history, logs, analytics, and the
Refererheader. - For session cookies, prefer server-set
HttpOnly,Secure, and an appropriateSameSitevalue. - Do not trust
navigator.userAgent,location, or storage values as proof of identity or authorization. Validate important decisions on the server. - Escape or safely render values read from storage, URLs, or cookies. Never insert untrusted values with
innerHTML.
Rule of thumb: use storage for preferences and drafts, cookies for server-managed sessions, and server-side validation for anything security-sensitive.
- The BOM lets JavaScript interact with the browser beyond the page content.
- window is the global object for classic scripts in a browser page and provides access to many browser APIs.
-
history lets you navigate back and
forward in the session history, add entries with
pushState, replace the current entry withreplaceState, and respond to Back or Forward withpopstate. - navigator provides information about the browser and device.
- screen gives display information, with dimensions reported in CSS pixels.
- location holds the current URL and lets you navigate to another page.
- Cookies are small browser-stored values that may be sent with matching HTTP requests.
- localStorage stores data persistently for an origin until it is removed or cleared.
- sessionStorage stores data only for the current tab session.
Apply these APIs in small projects that have real browser state and user workflows:
Weather app Todo list Quiz appSecurity reminder: storage and browser metadata are convenient, not trusted. Keep secrets out of client storage and validate authorization on the server.