Complete JavaScript Course Module 11: Intermediate: Useful Built-in Features

Saving Data with localStorage and sessionStorage

  • Beginner
  • Lesson 11.4
  • 5 min read
  • 50 of 76 in the course

In short

Web storage lets your page remember things after a reload. In this lesson you will learn how to save data with localStorage and sessionStorage, store objects with JSON, and use storage safely. What is localStorage? localStorage is a small storage box that the browser keeps for each website.

Web storage lets your page remember things after a reload. In this lesson you will learn how to save data with localStorage and sessionStorage, store objects with JSON, and use storage safely.

What is localStorage?

localStorage is a small storage box that the browser keeps for each website. Data you put in it stays there after the page reloads, and even after the browser is closed and opened again. It is like a notebook the website keeps in your browser. It is perfect for small preferences: a theme, a language, a draft message, a saved list.

The data belongs to one origin (the protocol, domain and port, like https://codecraft.example). Other websites cannot read it.

setItem, getItem and removeItem

Storage works with keys and values, like a labelled drawer. There are four main methods:

  • localStorage.setItem(key, value) saves a value.
  • localStorage.getItem(key) reads it back, or returns null if the key does not exist.
  • localStorage.removeItem(key) deletes one key.
  • localStorage.clear() deletes everything for this site.
localStorage.setItem("username", "Maya");
localStorage.setItem("visits", 3);

console.log(localStorage.getItem("username"));
// Output: Maya
console.log(localStorage.getItem("visits"));
// Output: 3
console.log(typeof localStorage.getItem("visits"));
// Output: string
console.log(localStorage.getItem("favouriteColour"));
// Output: null

localStorage.removeItem("username");
console.log(localStorage.getItem("username"));
// Output: null

Run this in the console, then reload the page and run localStorage.getItem("visits") again: the value is still there. Notice that the number 3 came back as the string "3". Storage keeps only strings. Use Number() to turn it back into a number.

You can see and edit stored data in your browser's developer tools, under the Application tab (Chrome, Edge) or Storage tab (Firefox).

How to store objects and arrays with JSON

If you save an object directly, it turns into the useless string "[object Object]". Instead, convert it to JSON text with JSON.stringify() before saving, and back with JSON.parse() after reading. You saw both in the JSON lesson.

const cart = [
  { name: "T-shirt", size: "M", qty: 2 },
  { name: "Cap", size: "One size", qty: 1 },
];

localStorage.setItem("cart", JSON.stringify(cart));

const loadCart = () => {
  try {
    return JSON.parse(localStorage.getItem("cart")) ?? [];
  } catch {
    return [];
  }
};

const savedCart = loadCart();
console.log(savedCart.length);
// Output: 2
console.log(savedCart[0].name);
// Output: T-shirt

JSON.parse(null) gives null, so ?? [] gives us an empty array when nothing is saved yet. The try...catch protects us if the stored text is broken, for example if someone edited it by hand in developer tools.

Common mistake: Calling localStorage.setItem("cart", cart) without JSON.stringify. You will read back "[object Object],[object Object]" and your data is lost.

What is the difference between localStorage and sessionStorage?

sessionStorage has exactly the same methods. The difference is how long the data lives.

localStoragesessionStorage
Survives a page reloadYesYes
Survives closing the tabYesNo
Shared between tabs of the same siteYesNo, each tab has its own
Good forPreferences, saved listsA multi-step form, one visit's temporary state
sessionStorage.setItem("checkoutStep", "2");
console.log(sessionStorage.getItem("checkoutStep"));
// Output: 2

Close the tab and open the site again, and checkoutStep is gone.

Storage limits and privacy

Web storage is simple, but it has limits:

  • Each site gets about 5 MB. Saving more throws an error (a QuotaExceededError), so wrap big saves in try...catch.
  • It is synchronous: every read and write pauses your code for a moment. Keep the data small.
  • Some browsers clear it in private windows or after a long time without visits. Never treat it as the only copy of important data.

The most important rule is about safety. Any JavaScript running on your page can read localStorage, including third-party scripts and code injected by an XSS attack. Anyone with access to the computer can read it in developer tools too.

Note: Never store passwords, credit card numbers or other secrets in localStorage. Be very careful with login tokens; many sites keep those in secure, HttpOnly cookies set by the server, which JavaScript cannot read. Use web storage for harmless things like preferences.

Example: remember my theme

Let's build a dark mode switch that remembers the choice. On load, we read the saved theme. If there is none, we follow the visitor's system setting.

<!DOCTYPE html>
<html lang="en">
  <head>
    <style>
      body { font-family: system-ui, sans-serif; background: #ffffff; color: #1a1a1a; transition: background 0.2s; }
      body.dark { background: #121212; color: #f0f0f0; }
    </style>
  </head>
  <body>
    <h1>My blog</h1>
    <button id="theme-toggle" aria-pressed="false">Dark mode</button>

    <script>
      const THEME_KEY = "theme";
      const button = document.querySelector("#theme-toggle");

      const applyTheme = (theme) => {
        const isDark = theme === "dark";
        document.body.classList.toggle("dark", isDark);
        button.textContent = isDark ? "Light mode" : "Dark mode";
        button.setAttribute("aria-pressed", String(isDark));
      };

      const prefersDark = window.matchMedia("(prefers-color-scheme: dark)").matches;
      const savedTheme = localStorage.getItem(THEME_KEY);
      applyTheme(savedTheme ?? (prefersDark ? "dark" : "light"));

      button.addEventListener("click", () => {
        const newTheme = document.body.classList.contains("dark") ? "light" : "dark";
        applyTheme(newTheme);
        localStorage.setItem(THEME_KEY, newTheme);
        console.log(`Saved theme: ${newTheme}`);
      });
    </script>
  </body>
</html>
Saved theme: dark

Click the button and the page turns dark. Reload, and it stays dark, because we read "dark" from storage before anything else. classList.toggle("dark", isDark) uses a second argument: it adds the class when isDark is true and removes it when false. window.matchMedia checks the operating system's colour preference for first-time visitors.

Practice exercise

Make a "notes" box: a <textarea> that saves its text to localStorage on every input event and loads it back when the page opens. Add a "Clear" button that empties the box and removes the key. Then change it to use sessionStorage and compare what happens when you close the tab.

Hint: Load first with textarea.value = localStorage.getItem("note") ?? "";.

Key takeaways

  • localStorage keeps data per site across reloads and browser restarts; sessionStorage lasts only for one tab.
  • Use setItem, getItem (returns null if missing), removeItem and clear.
  • Storage holds only strings: use JSON.stringify to save objects and JSON.parse to read them.
  • The limit is about 5 MB per site, and any script on the page can read the data.
  • Never store passwords or sensitive secrets in web storage.