// web · http

How HTTP works: the conversation behind every page

Every page load, API call, and image on the web is an HTTP exchange: a client asks, a server answers. This guide walks the whole conversation — messages, status codes, cookies, and connections — with an interactive simulator for each. Press play.

mindmap — quick refresh HTTP — the web's conversation players client — always asks first proxies — cache · filter · balance server — answers message shape start line: method · path · version headers = extensibility (Host, Accept-*) blank line, then body same anatomy both directions status codes 2xx success 3xx redirect — follow Location 4xx client's fault → fix the request 5xx server's fault → fix the server state stateless core (a feature!) Set-Cookie → Cookie client carries the token; server looks it up connections ride on TCP (+ TLS) 1.0: handshake per resource 1.1: persistent, serial 2: one connection, multiplexed 3: QUIC — handshake nearly free headers control everything else caching (Cache-Control, ETag) CORS auth content negotiation

Prerequisites: none — this is the first stop on the web-fundamentals path. Everything else builds on it.

Three facts explain almost everything about HTTP:

  1. The client always speaks first. A server can't call your browser out of the blue — every exchange starts with a request and ends with a response. Everything the web does is built from that one shape.
  2. It's text you can read. An HTTP/1.1 request is a few lines of plain text — you can type one by hand into a raw TCP connection and a real server will answer you. That simplicity is deliberate, and it's why the protocol was easy to extend for 30+ years.
  3. It remembers nothing. HTTP is stateless by design: each request arrives with no memory of the last one. Every login session, shopping cart, and "stay signed in" checkbox is a workaround built on top — with cookies.

Let's walk the conversation end to end. Each concept has a simulator — press play or step through them.

Who's talking: client, proxies, server

HTTP is a client–server protocol. The client (your browser, curl, a mobile app — anything acting on your behalf) sends requests; the server answers with documents or data. But between them, the request usually passes through proxies — machines that can cache responses, filter content, balance load across servers, or log traffic, all without either end doing anything special:

The cache hit at the end is the important part: a proxy that already holds a fresh copy can answer instantly without bothering the origin server. Much of web performance engineering is arranging for exactly that to happen — which is why HTTP has an entire vocabulary of caching headers.

The message: a few lines of text

Here's a complete, real HTTP/1.1 exchange — first the request, then the response:

GET /guide.html HTTP/1.1
Host: learn.kevalabs.com
Accept-Language: en
HTTP/1.1 200 OK
Date: Sat, 16 Aug 2026 07:28:00 GMT
Server: keva-edge
Content-Type: text/html
Content-Length: 29769

<!doctype html>… (29,769 bytes of HTML)

Every request and response has the same anatomy — a start line, headers, a blank line, and an optional body. Step through each part:

Two details worth keeping: the Host header is what lets one machine serve many websites from a single IP address, and headers in general are HTTP's extension mechanism — new capabilities (caching rules, CORS, compression, auth) arrive as new headers, not new protocols. HTTP/2 encodes all of this in binary frames for efficiency, but the semantics are identical — what you learn here transfers unchanged.

Status codes: the server's verdict

The first line of every response carries a three-digit status code. The first digit tells you who's happy and who's at fault:

The classes matter more than memorizing individual codes: 2xx means success, 3xx means "look elsewhere" (the client follows automatically), 4xx means the client asked for something wrong, 5xx means the server broke while answering a valid request. That 4xx/5xx distinction is the first thing to check when debugging: it tells you which side of the wire to look at.

Stateless by design, sessions by cookies

HTTP treats every request as if it came from a stranger. That sounds like a flaw; it's actually what lets one server (or a hundred, behind a load balancer) handle millions of clients without keeping a conversation open for each. But then, how does a shopping cart survive from one click to the next?

The trick: the server hands the client a small token (Set-Cookie), and the client volunteers it back on every subsequent request (Cookie). The client carries the memory; the server just uses the token to look up state on its side. Sessions, logins, and "remember me" are all this one mechanism.

One connection or many

HTTP messages ride on TCP connections (with TLS on top for HTTPS), and how those connections are used changed dramatically across versions. Watch six resources being fetched under each model:

HTTP/1.0 paid a full TCP handshake for every resource. HTTP/1.1 introduced persistent connections — one handshake, requests one after another. HTTP/2 multiplexes: many requests and responses interleaved on a single connection at once, so one slow response no longer blocks the rest. HTTP/3 goes further, replacing TCP with QUIC so even the transport handshake all but disappears. (For why handshakes and round trips are so expensive in the first place, the next guide walks the full journey — How browsers work.)

What else rides on headers

Almost every other HTTP capability is "just headers," which is the payoff of fact #2 — an extensible, readable protocol:

  • CachingCache-Control, ETag, Last-Modified: the server tells clients and proxies what may be stored, and for how long.
  • Cross-origin access (CORS)Origin and Access-Control-*: servers selectively relax the browser's same-origin rules.
  • AuthenticationWWW-Authenticate / Authorization, or cookie-based sessions.
  • Content negotiationAccept, Accept-Language, Content-Encoding: the same URL can serve French text or compressed bytes to the clients that ask for them.

Takeaways

  • Everything is request → response, client-first. If a design seems to need the server to speak first, you need a different mechanism (Server-Sent Events, WebSockets) — both of which start life as an HTTP request.
  • Read the raw messages when debugging. HTTP is text (or binary framing of the same semantics); curl -v shows you the actual conversation, and it settles arguments fast.
  • Status class before status code: 4xx → fix the request, 5xx → fix the server, 3xx → follow the trail.
  • Cookies are the client carrying the server's memory. Statelessness is a feature; treat session state as an explicit, deliberate add-on.
  • Fewer connections, fewer handshakes. Connection reuse and multiplexing are where whole round trips are won — the same lesson the next guide teaches from the browser's side.

References

  • Barth, A. (2011). HTTP state management mechanism (RFC 6265). Internet Engineering Task Force. https://doi.org/10.17487/RFC6265
  • Bishop, M. (2022). HTTP/3 (RFC 9114). Internet Engineering Task Force. https://doi.org/10.17487/RFC9114
  • Fielding, R., Nottingham, M., & Reschke, J. (2022a). HTTP/1.1 (RFC 9112). Internet Engineering Task Force. https://doi.org/10.17487/RFC9112
  • Fielding, R., Nottingham, M., & Reschke, J. (2022b). HTTP semantics (RFC 9110). Internet Engineering Task Force. https://doi.org/10.17487/RFC9110
  • MDN Web Docs. (n.d.). Overview of HTTP. Mozilla. Retrieved August 16, 2026, from https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/Overview
  • Thomson, M., & Benfield, C. (2022). HTTP/2 (RFC 9113). Internet Engineering Task Force. https://doi.org/10.17487/RFC9113

Structure follows MDN's Overview of HTTP (CC-BY-SA); the prose, mistakes, and simulators are ours.