Everything we covered — local servers, HTTP, headers, caching, origins, ports, CDNs, and DNS — in one place you can click through and explore.
The word server is doing double duty. It refers to a physical machine and to a piece of software. Most confusion comes from mixing those two up.
Pick your tool and run this in your terminal, from any folder you want to serve.
# Navigate to the folder you want to serve cd ~/my-project # Start a server on port 8080 python3 -m http.server 8080 # Open your browser to: http://localhost:8080
127.0.0.1 — a reserved IP that means "this machine talking to itself." Never leaves your computer.
Every time your browser loads something, it sends a structured text message to a server and gets a structured text message back. HTTP is just a protocol — an agreed format for those messages.
GET /index.html HTTP/1.1 Host: localhost:8080 Accept: text/html Connection: keep-alive ← blank line separates headers from body --- server responds --- HTTP/1.1 200 OK Content-Type: text/html Cache-Control: max-age=3600 ← blank line separates headers from body <html>...</html> ← the actual file
Headers are metadata that travel alongside a request or response — separate from the content itself. Think of them as the label on the outside of a shipping package.
Browser → Server. Who's asking, what they accept, cookies they carry, and how they want the response.
Server → Browser. What type of content it is, how to cache it, what cookies to set, security rules to apply.
Always plain text key-value pairs. Key: Value. A blank line separates headers from the body.
Subclass SimpleHTTPRequestHandler and override end_headers() to inject your own.
Cache this file. Treat it as fresh for this many seconds before re-requesting.
Store it, but always check the server before using the cached copy.
Never store this anywhere. Request fresh from server every single time.
CDNs and browsers are both allowed to cache this file.
Browser only. CDN must not cache this — it's user-specific.
Serve the stale copy instantly, fetch a fresh one in the background.
from http.server import SimpleHTTPRequestHandler, HTTPServer class CachedHandler(SimpleHTTPRequestHandler): def end_headers(self): self.send_header("Cache-Control", "max-age=3600") self.send_header("X-Custom-Header", "hello") super().end_headers() HTTPServer(("", 8080), CachedHandler).serve_forever()
An origin is three things: protocol + domain + port. Change any one of them and you have a different origin. The browser uses this to enforce security boundaries between sites.
URL A (reference origin)
URL B — click to change each piece
The path (/home, /messages) is always ignored when comparing origins.
http://localhost:8080 — so fetch(), ES modules, and cookies all work.
Every machine has 65,535 ports. Think of them as parking spots — not permanently owned, just grabbed on demand. One process per spot at a time.
http://
protected
https://
protected
A cache is a saved copy of something so you don't have to fetch it again. There are four layers, each positioned closer to the user than the one before it.
A CDN puts copies of your files on servers around the world. Users get files from the nearest location instead of your one origin server. First request populates the edge. Every request after that is served locally.
main.a3f9.js → main.b81d.js. New filename = new cache entry. No CDN purge needed. Your HTML always points to the new file, and the old one expires naturally.
You type twitter.com. The internet speaks in IP addresses. DNS translates between the two — every single time, in milliseconds, invisibly.