What you'll learn
Browser storage persists state across interactions and visits, but each option has different capacity, query, lifetime, privacy, and security properties.
By the end of this lesson, you'll be able to:
- Choose Web Storage or IndexedDB
- Version serialized state
- Avoid persisting secrets
Core mental model
Use this decision table as a compact reference. Focus on what each tool means and when it earns its place in production code.
| Concept | What it means | Decision rule |
|---|---|---|
| localStorage | Synchronous string storage for an origin | Use only for small, non-sensitive preferences |
| sessionStorage | String storage scoped to one tab session | Use for disposable per-tab state |
| IndexedDB | Async transactional object database | Use for substantial structured or offline data |
Professional workflow
Build the behavior in small, observable steps. Each step should leave something you can inspect or test.
- Describe the client storage boundary: inputs, outputs, state, timing, and expected failures.
- Implement the smallest correct path with names that expose intent.
- Add edge cases and failure handling before introducing abstractions.
- Verify behavior with realistic data and one deliberately adversarial example.
- Refactor only after the observable behavior is protected.
Make behavior observable
Guided code lab
Persist a versioned preference
Versioning gives future code a migration decision instead of blindly trusting old data.
const key = "course-preferences";
const preferences = { version: 1, theme: "dark", compact: false };
localStorage.setItem(key, JSON.stringify(preferences));
const saved = JSON.parse(localStorage.getItem(key) ?? "null");
console.log(saved?.version === 1 ? saved.theme : "default");Recover from corrupted storage
Stored state is external input and must be parsed defensively.
function readJson(key, fallback) {
try {
const raw = localStorage.getItem(key);
return raw === null ? fallback : JSON.parse(raw);
} catch {
localStorage.removeItem(key);
return fallback;
}
}Production practice
Contract
Keep the client storage API explicit: accepted state, emitted events, DOM ownership, and cleanup.
Verification
Test with keyboard input, missing elements, repeated initialization, and teardown—not only a mouse happy path.
Operations
Measure user-visible latency and remove listeners, observers, object URLs, or media tracks when the feature ends.
Common failure mode
Independent workshop
Add durable preferences and recoverable draft state to a lesson-notes feature.
Your finished workshop must include:
- Namespaced versioned keys
- Corruption fallback
- A documented retention and privacy policy
Definition of done
Recap & quick check
Key takeaways
- Web Storage is synchronous and string-only
- IndexedDB is async and structured
- Stored data needs validation and versioning
- Do not store secrets casually
Quick check
1. What type does localStorage return?
2. Which API fits large structured offline data?
3. Is stored JSON trusted input?
Keep the workshop. Later modules deliberately build on these decisions, so each exercise can become part of your final portfolio architecture.