Learn / Infrastructure / Lesson 08
Edge caching
A CDN can serve your pages from a city near the visitor in milliseconds, or serve one person's account page to thousands of strangers. The headers decide which.
Last updated: 2026-09-19
What it is
A CDN (content delivery network) such as Cloudflare keeps copies of your responses in data centres around the world, called the edge. When a visitor in Manila asks for a page, the copy in Manila answers, and your server never hears about it.
What the edge may keep, and for how long, is decided by one header on your response: Cache-Control.
Why it is a rule
- Steam, Christmas Day 2015. Under a heavy attack, Valve changed its caching setup. For about an hour, account pages were cached and served to other people: names, addresses, the last digits of cards and purchase history. Valve later said around 34,000 users had their details shown to someone else. Nothing was hacked. A page meant for one person had been marked as safe to share.
The lesson: caching a page that varies by person is not a performance bug. It is a data breach.
How to do it
Know the directives
| Directive | Meaning |
|---|---|
public | Any cache may keep it, including the CDN |
private | Only the visitor's own browser may keep it |
no-store | Nobody keeps it, ever |
no-cache | Keep it, but check with the server before each use |
max-age=N | The browser may use it for N seconds |
s-maxage=N | Shared caches (the CDN) may use it for N seconds; overrides max-age there |
immutable | This URL's content will never change; do not even revalidate |
Sort every response into one of three kinds
Same for everyone, changes on deploy → public, max-age=0, s-maxage=31536000
Same for everyone, never changes → public, max-age=31536000, immutable
Different per person, or has a secret → private or no-store- Marketing pages and articles go in the first group. The CDN keeps them for a long time; browsers always ask again, so a deploy shows up at once.
- Versioned assets (
app.js?v=abc123) go in the second. A new deploy uses a new URL, so the old one can be cached forever. See the deploys lesson. - Anything that reads a cookie or a session goes in the third, and APIs are
no-store.
Purge on deploy
A long s-maxage is only safe if every deploy clears the edge. The new server purges the CDN as it boots, so no visitor sees an old page after a release.
Keep the list short and explicit
Decide per page, in one place, which paths may be edge-cached. Everything else defaults to not cached. A page added later is then safe by default.
How we do it here
Only pages that are identical for every visitor are edge-cached: the home page, About, the legal pages and these lessons. They are cached at Cloudflare until the next deploy, which purges the cache when the new server starts. Anything that reads a session, and every API response, is never stored at the edge.
Benefits
- Pages load from a nearby city, often in tens of milliseconds.
- The origin server does almost no work for public traffic, and survives spikes.
- The CDN keeps serving the public pages even while the origin restarts.
Disadvantages
- One wrong header is a breach, not a slowdown, as Steam showed.
- Purging depends on the CDN's API. If the purge fails, visitors see the old site until it succeeds.
- Debugging gets harder: "it works on my machine" can mean "the edge still has yesterday's copy".
Checklist
- Every edge-cached path is listed explicitly.
- Nothing that reads a cookie or session is on that list.
- APIs send
no-store. - Each deploy purges the edge, and a failed purge is logged loudly.
Sources
- MDN — Cache-Control
- RFC 9111 — HTTP Caching
- Valve, statement on the Steam caching incident of 25 December 2015.