Latency is bounded by the speed of light, so no amount of backend optimization helps a user thousands of miles from your origin server — a round trip from Mumbai to a us-east origin is going to cost roughly 200ms no matter how fast your database is. A CDN caches content at geographically distributed edge locations (PoPs) so the response never has to make that trip at all. Understanding cache hit/miss behavior, not just "CDNs make things faster," is essential for any system-design discussion involving global scale.
A CDN (Content Delivery Network) is a network of servers spread across many physical locations around the world that store copies of a website's content close to the people requesting it. Instead of every visitor's request traveling all the way to one central server, it's answered by a nearby copy, which makes the page or video load faster.
Think of a popular pizza chain. Instead of baking every pizza in one central kitchen and shipping it across the country, the chain opens local branches in every neighborhood, each stocked with the same recipe and ingredients. When you order, the nearest branch makes it, so you get a hot pizza in twenty minutes instead of waiting days for one to arrive from headquarters.
Cache HIT (common case, fast path):
User --> Nearest Edge PoP --[cache has it]--> served directly
Latency ~= physical distance to nearest PoP only (often <20ms)
Cache MISS (first request for an object, or expired TTL):
User --> Nearest Edge PoP --[miss]--> Origin Server
<--response--
edge CACHES the response, then --> serves User
Latency = distance-to-edge + distance-to-origin + origin processing
Subsequent nearby users then get a HIT from that same edge.The core interview insight: a CDN's value compounds — the first user in a region "pays" the miss cost and warms the cache; every user after them in that region gets the hit-path latency until the TTL expires. This is also why a cold, rarely-requested object (the "long tail") gets little CDN benefit — it's effectively always a miss.
Vary/cache-control rules.# Check whether a response was a CDN hit or miss — look for
# X-Cache, CF-Cache-Status, Age, or similar headers
curl -sI https://example.com/static/logo.png | grep -i "cache\|age\|x-served"
# Compare timing for a cached static asset vs an uncached/dynamic
# endpoint using curl's timing breakdown
curl -w "@curl-format.txt" -o /dev/null -s https://example.com/static/app.js
curl -w "@curl-format.txt" -o /dev/null -s https://example.com/api/data
# curl-format.txt contents:
# time_namelookup: %{time_namelookup}\n
# time_connect: %{time_connect}\n
# time_starttransfer: %{time_starttransfer}\n
# time_total: %{time_total}\n
# Request the same resource twice in a row — second request should
# show a HIT and a much lower time_starttransfer
curl -sI https://example.com/static/app.js | grep -i x-cache
curl -sI https://example.com/static/app.js | grep -i x-cache
# Inspect actual cache-control policy being sent by origin/edge
curl -sI https://example.com/ | grep -i "cache-control\|expires\|vary"
Q: Walk me through what happens on a cache miss for a brand-new object.
A: The request reaches the nearest edge PoP, the edge checks its local cache, finds nothing (miss), and forwards the request upstream — either directly to origin or through a shield tier if one exists. The origin generates the response, the edge stores it according to the response's cache-control/TTL headers, and finally serves it to the requesting user. Every subsequent request for that same object from users near that edge is now served as a hit until the TTL expires or it's explicitly purged.
Q: How do you avoid stale content being served after you deploy a fix?
A: Either set short TTLs for content that changes often, use cache-busting via versioned/fingerprinted URLs (e.g. app.a1b2c3.js) so a new deploy is automatically a new cache key, or issue an explicit purge/invalidation call to the CDN provider's API. Versioned filenames are generally preferred over purging because purges have propagation delay across thousands of edge nodes and can be rate-limited by the provider.
Q: Can you cache API responses, and what makes that safe or unsafe?
A: Yes, when the response is not personalized (or personalization is captured correctly via a Vary header, e.g. varying on an auth token or locale) and a bounded staleness window is acceptable. Unsafe caching usually comes from forgetting to vary on something that affects the response — caching a personalized response as if it were shared would leak one user's data to another.
In "design a system serving global users" questions (video platform, image-heavy social feed, e-commerce catalog), the CDN is the first layer you should mention for anything static or infrequently-changing — it removes both latency and load from every other component in the design. It also comes up directly when asked "how would you handle a traffic spike" (edge absorption) or "how would you defend against a DDoS attack" (volumetric traffic dies at the edge rather than reaching origin capacity). When a design includes user-generated content or personalization, expect a follow-up on how you'd decide what's cacheable vs what must hit origin — that's exactly the shield-caching / cache-key discussion above.
CDNs cut latency and origin load dramatically but introduce cache-invalidation complexity — stale content, purge propagation delay across thousands of PoPs, and correctness risk for personalized or rapidly changing responses. Interview gotcha: know the cache-control directives (max-age, no-store, stale-while-revalidate) and how tiered/shield caching reduces origin fan-out when many edge nodes miss on the same cold object at once — this is the difference between "the CDN helps" and "the CDN survives a launch-day traffic spike."