AnyLearn
All lessons

CDNs Explained

Why your assets should never come from your origin. How a CDN's edge cache, geographic routing, and invalidation actually work, plus the cases where a CDN doesn't help (or quietly hurts).

Not signed in โ€” your progress and quiz score won't be saved.
Lesson progress1 / 8

What a CDN is

A Content Delivery Network is a fleet of servers ("edges" or "PoPs") distributed worldwide, each holding cached copies of your content. When a user requests a file, the CDN serves it from whichever edge is closest to them โ€” not from your origin in us-east-1.

Three wins:

  1. Speed: a user in Tokyo gets your CSS from a Tokyo PoP in 10ms instead of from Virginia in 200ms.
  2. Origin offload: 95% of asset requests never reach your servers. Your bandwidth bill and capacity needs shrink.
  3. Resilience: a CDN absorbs traffic spikes (and many DDoS attempts) before they hit your origin.

The trade: cached data can be stale, and you have to think about how to invalidate it.

Full lesson text

All 8 steps on one page โ€” for reading, reference, and search.

Show

1. What a CDN is

A Content Delivery Network is a fleet of servers ("edges" or "PoPs") distributed worldwide, each holding cached copies of your content. When a user requests a file, the CDN serves it from whichever edge is closest to them โ€” not from your origin in us-east-1.

Three wins:

  1. Speed: a user in Tokyo gets your CSS from a Tokyo PoP in 10ms instead of from Virginia in 200ms.
  2. Origin offload: 95% of asset requests never reach your servers. Your bandwidth bill and capacity needs shrink.
  3. Resilience: a CDN absorbs traffic spikes (and many DDoS attempts) before they hit your origin.

The trade: cached data can be stale, and you have to think about how to invalidate it.

2. Pull-through vs push CDNs

Two ways content gets to the edge:

  • Pull CDN (the default): edges fetch from your origin on first miss, cache, and serve. You change nothing about how you publish files. Cloudflare, AWS CloudFront, Fastly all default to pull. Use this 95% of the time.
  • Push CDN: you upload assets to the CDN explicitly. The edge serves them; the origin never gets asked. Used for predictable static content, large video libraries, or strict origin-shield requirements.

For most apps, pull is dramatically simpler and works fine. Push starts making sense when origin egress costs matter and you want to control exactly what lives on the edge.

3. Cache hierarchy

A request from your browser passes through several caches in a typical CDN setup:

  1. Browser cache: the user's machine. Fastest; controlled via Cache-Control headers.
  2. Edge PoP: the CDN node serving the user. Most traffic terminates here.
  3. Regional cache / shield: a few large mid-tier caches in front of origin. Coalesces requests from many edges so origin sees one request, not many.
  4. Origin: your servers.

A cache MISS at one layer is a HIT or MISS at the next. Tuning Cache-Control and the CDN's edge TTL controls how long each layer holds onto things. The further down the hierarchy a request reaches, the slower it is.

4. Cache hierarchy in a typical CDN

Each layer absorbs traffic from the next.

flowchart LR
  User["Browser"] --> Edge["Edge PoP"]
  Edge --> Shield["Regional shield"]
  Shield --> Origin["Origin server"]

5. TTLs and Cache-Control

Your origin's Cache-Control header tells everyone downstream how long to cache. Common patterns:

  • Cache-Control: public, max-age=31536000, immutable โ€” assets with content-hashed filenames (app.a8b3.js). Cache forever; new versions get new URLs.
  • Cache-Control: public, max-age=300, s-maxage=3600 โ€” HTML or APIs with mild freshness. Browser caches 5 min; CDN caches 1 hour (s-maxage overrides for shared caches).
  • Cache-Control: private, no-store โ€” user-specific or sensitive responses. Never cached.
  • Cache-Control: public, max-age=0, must-revalidate, stale-while-revalidate=86400 โ€” always check freshness, but tolerate stale during revalidation. The pattern modern frameworks use for most pages.

Get these right and the CDN does the rest. Get them wrong and you ship stale builds for hours.

6. Invalidation: the painful part

Sometimes you need to forcibly clear something from every edge worldwide. Approaches:

  1. Content-hashed URLs: never invalidate at all. New version โ†’ new URL (app.a8b3.js โ†’ app.de91.js). The most reliable approach; ideal for build artifacts.
  2. Versioned URLs (?v=42): similar idea; bump the query string to bust caches. Note: some CDNs ignore query strings by default; check.
  3. API-driven purge: most CDNs let you POST a URL to a purge endpoint. Reliable for content you can enumerate (specific pages). Often rate-limited.
  4. Surrogate keys / tags: Fastly and others let you tag cached objects with keys, then purge all objects with a key in a single request. Game-changing for content with cross-cutting dependencies.

Rule of thumb: design URLs so you almost never need to invalidate, then use API purges for the rare case.

7. Edge compute, briefly

Modern CDNs let you run code at the edge โ€” Cloudflare Workers, Fastly Compute, Vercel Edge Functions, AWS Lambda@Edge. The pitch: response generation closer to the user, sub-millisecond cold starts, no origin round-trip.

Good fits:

  • A/B testing routing
  • Auth checks before forwarding to origin
  • Image resizing on the fly
  • Personalisation of cached HTML

Less good fits: anything that needs a database in another region (you've moved the latency, not eliminated it), heavy compute (edge runtimes are constrained), or strong consistency across PoPs (replication latency is real).

Useful, not magic. The shape of the problem still matters.

8. When a CDN doesn't help

CDNs are most powerful for public, cacheable, repeated responses. They help less or not at all for:

  • Per-user dynamic responses: each user gets a different page; nothing cacheable at the edge.
  • Write-heavy APIs: nothing to cache; the CDN is just a passthrough proxy.
  • WebSockets and long-lived connections: CDNs can proxy them but the caching benefit is zero.
  • Geographically uniform audiences: if 99% of your users are in one city, the CDN's geographic spread is wasted (though origin shielding can still help).

In these cases the CDN's value drops to "sane TLS termination + DDoS protection" โ€” still nice, but you wouldn't pay enterprise pricing just for that. Match the tool to the workload.

Check your understanding

The lesson ends with a 5-question quiz. Take it in the player above to see your score.

  1. What is the primary purpose of a CDN's regional shield or mid-tier cache?
    • To replace the origin server
    • To coalesce many edge cache-misses into a small number of origin requests
    • To enforce TLS
    • To rewrite URLs
  2. Which approach is the most reliable way to ship a new version of `app.js` without serving stale copies?
    • Lower the CDN's TTL to 1 minute
    • Use content-hashed filenames; old versions stay cached but the new URL is fetched fresh
    • Send a purge request for `app.js` and wait
    • Restart the origin server
  3. When does `Cache-Control: public, max-age=300, s-maxage=3600` apply each value?
    • max-age = browser, s-maxage = CDN/shared caches
    • max-age = origin, s-maxage = browser
    • Both apply to the browser
    • max-age = mobile, s-maxage = desktop
  4. Which workload benefits *least* from a CDN's caching?
    • Public homepage of a marketing site
    • Per-user dashboard rendered server-side from session state
    • Library of static JavaScript bundles
    • Public blog posts
  5. What's a typical reason to use edge functions (Cloudflare Workers, Vercel Edge Functions) instead of pure static caching?
    • Static caches can't handle gzip
    • You need lightweight per-request logic (A/B routing, auth checks, image resizing) close to users without a round-trip to origin
    • Edge functions are always cheaper
    • Static caches don't support HTTPS

Related lessons