Cache lifecycle simulator
Write a Cache-Control field, advance the clock, fire requests — and watch freshness and revalidation resolve.
Cache-Control: max-age=300- No exchanges yet — press Navigate to issue the first request.
Model figures: 138.7 kB body, 320 B of response headers, 120 ms round trip, 360 ms transfer. Decisions follow RFC 9111 freshness and validation, RFC 8246 (immutable) and RFC 5861 (stale-while-revalidate). Reload is modelled as an ordinary browser reload — a conditional request carrying Cache-Control: max-age=0 — not a force reload.
Freshness, then validation
A stored response is reusable without contacting the origin while its current age is below its freshness lifetime — that is the whole of the fast path, and it costs zero bytes. Once age passes lifetime the response is stale, which does not mean unusable: it means the cache must revalidate before reuse.
Revalidation sends a conditional request carrying the stored validator. If nothing changed the origin answers 304 Not Modified with no body, and the cache updates the stored headers and restarts the freshness clock. The saving is the body, which is almost all of the bytes.
The directives that are routinely confused
no-cache does not mean do not store. It means store, but revalidate before every reuse. The directive that prevents storage is no-store. must-revalidate only bites once a response is already stale — it forbids serving stale, it does not shorten freshness.
Two extensions change the shape of the timeline. immutable (RFC 8246) tells the cache not to revalidate even when the user reloads, which is why hashed asset URLs can be served indefinitely. stale-while-revalidate (RFC 5861) lets a cache serve a stale response immediately while refreshing in the background, moving the latency off the reader and onto the cache.