← all topics

8 · HTTP ★

Slides 2-16 → 2-46 (minus caching) · HW2 P0, P1, P2

HTTP basics

Two kinds of connections

Non-persistent (HTTP/1.0)Persistent (HTTP/1.1, the default)
Open a TCP connection, send at most one object, close itThe server leaves the connection open after responding
Multiple objects → multiple connectionsMultiple objects go over one connection
2 RTT per object, plus OS overhead for every connectionAs little as 1 RTT for all the referenced objects
Browsers open parallel connections to speed things upWith pipelining, the client sends requests as soon as it finds each referenced object
What "pipelining" means: on a persistent connection, the client sends all its requests back-to-back without waiting for each response.
• No pipelining: send GET 1 → wait for object 1 → send GET 2 → wait… That's 1 RTT per object.
• Pipelining: send GET 1, GET 2, …, GET 8 all at once → the responses stream back. That's about 1 RTT for all of them.
It's the same idea as segmentation in topic 4: keep the pipe full instead of waiting for each step to finish.

Where "2 RTT" comes from

RTT (round-trip time) = time for a small packet to go from client to server and back.

  1. 1 RTT to set up the TCP connection (client says hi, server says hi back).
  2. 1 RTT for the HTTP request to go out and the first bits of the response to come back.
  3. Plus the time to transmit the file.
$$\text{non-persistent response time (one object)} = 2\,\text{RTT} + \frac{L}{R}$$

Most problems say "neglect transmission time", so the \(L/R\) drops out.

The recipe (memorize this)

The page has a base HTML file and \(k\) referenced objects, all on the same server. \(\text{RTT}_0\) = RTT to that server.

$$T = \underbrace{\text{RTT}_1 + \dots + \text{RTT}_n}_{\text{DNS lookup}} \;+\; \underbrace{2\,\text{RTT}_0}_{\text{base HTML}} \;+\; \underbrace{\text{(objects)}}_{\text{depends on mode}}$$
ModeTime for the \(k\) objects
Non-persistent, no parallel\(k \cdot 2\,\text{RTT}_0\)
Non-persistent, \(p\) parallel connections\(\lceil k/p \rceil \cdot 2\,\text{RTT}_0\) (number of "rounds" × 2 RTT)
Persistent, no pipelining\(k \cdot \text{RTT}_0\) (one request at a time, no new handshakes)
Persistent, with pipelining (default)\(\text{RTT}_0\) (all requests sent back-to-back)
Traps
• The base HTML always costs 2 RTT₀, even with persistent HTTP: the TCP connection has to be set up first. Persistence only saves time on the later objects.
• The browser can't request the objects until it has parsed the HTML, so the objects always come after the base file. Don't fold them into the same round.
• DNS happens once, before anything else. It's \(\text{RTT}_1 + \dots + \text{RTT}_n\) (one RTT per DNS server, no handshake, because DNS uses UDP).
• Parallel rounds use the ceiling: 8 objects, 6 connections → 6 then 2 → 2 rounds, not 1.33.
• If transmission time is not neglected, add \(L/R\) for each object that's sent.

Worked example: HW2 P0

Q: Click a link. The IP isn't cached, so DNS visits \(n\) servers with RTTs \(\text{RTT}_1, \dots, \text{RTT}_n\). The page is one object (small HTML). \(\text{RTT}_0\) = RTT to the Web server. Zero transmission time. Total time?

$$T = \mathbf{\text{RTT}_1 + \dots + \text{RTT}_n + 2\,\text{RTT}_0}$$

DNS to get the IP, then 1 RTT for the TCP handshake and 1 RTT for the request/response.

Worked example: HW2 P1

Q: An HTTP client wants a URL, but the server's IP address is unknown. Which transport and application protocols besides HTTP are needed?

Worked example: HW2 P2

Q: Same as P0, but the HTML references 8 very small objects on the same server. Neglect transmission times.

(a) Non-persistent, no parallel connections

Every object needs its own connection: 8 × 2 RTT₀.

$$\text{RTT}_1 + \dots + \text{RTT}_n + 2\,\text{RTT}_0 + 8 \times 2\,\text{RTT}_0 = \mathbf{18\,\text{RTT}_0 + \text{RTT}_1 + \dots + \text{RTT}_n}$$

(b) Non-persistent, 6 parallel connections

\(\lceil 8/6 \rceil = 2\) rounds (6 objects, then the last 2), each 2 RTT₀.

$$\text{RTT}_1 + \dots + \text{RTT}_n + 2\,\text{RTT}_0 + 2 \times 2\,\text{RTT}_0 = \mathbf{6\,\text{RTT}_0 + \text{RTT}_1 + \dots + \text{RTT}_n}$$

(c) Persistent HTTP (with pipelining, the default)

The connection is already open, and all 8 requests go out back-to-back: 1 RTT₀.

$$\text{RTT}_1 + \dots + \text{RTT}_n + 2\,\text{RTT}_0 + \text{RTT}_0 = \mathbf{3\,\text{RTT}_0 + \text{RTT}_1 + \dots + \text{RTT}_n}$$
If they say persistent without pipelining: one request at a time, 1 RTT₀ each. $$\text{RTT}_1 + \dots + \text{RTT}_n + 2\,\text{RTT}_0 + 8\,\text{RTT}_0 = 10\,\text{RTT}_0 + \text{RTT}_1 + \dots + \text{RTT}_n$$

Side by side (just the RTT₀ part)

ModeBase HTML8 objectsTotal
Non-persistent, serial28 × 2 = 1618 RTT₀
Non-persistent, 6 parallel22 × 2 = 46 RTT₀
Persistent, no pipelining28 × 1 = 810 RTT₀
Persistent, pipelined213 RTT₀

Then add the DNS sum to every row.

HTTP messages

Two types: request and response. Both are ASCII (human-readable). Every line ends in \r\n (carriage return, line feed), and a blank line marks the end of the header lines.

Request

GET /index.html HTTP/1.1          ← request line: method, URL, version
Host: www-net.cs.umass.edu        ← header lines
User-Agent: Firefox/3.6.10
Connection: keep-alive
                                  ← blank line, then the (optional) body
MethodWhat it does
GETRequest an object. Can also send user data in the URL after a ? (e.g. animalsearch?monkeys&banana)
POSTSend user input (e.g. a form) to the server in the entity body
HEADAsk for only the headers a GET would return, not the object
PUTUpload a new file to the server, completely replacing the file at that URL

Response status codes (first line of the response)

CodeMeaning
200 OKRequest succeeded. The object is later in this message
301 Moved PermanentlyObject moved. New location is in the Location: header
400 Bad RequestServer didn't understand the request
404 Not FoundRequested document isn't on this server
505 HTTP Version Not Supported

Also coming up in topic 9: 304 Not Modified (conditional GET). The response uses a Content-Length: header to say how long the body is (that's HW2 P4, topic 10).

Cookies: keeping state on a stateless protocol

Four components:

  1. A Set-cookie: header line in the HTTP response
  2. A Cookie: header line in the next HTTP requests
  3. A cookie file on the user's host, managed by the browser
  4. A back-end database at the Web site

Flow: Susan visits Amazon for the first time. The server creates a unique ID (say 1678) and a database entry for it, and replies with Set-cookie: 1678. Her browser stores it. Every later request to Amazon, even a week later, carries Cookie: 1678, so the site recognizes her and takes a cookie-specific action.

HTTP/2 and HTTP/3

Goal of both: less delay for pages with many objects.

VersionKey points
HTTP/1.1Pipelined GETs over one TCP connection, but the server replies in order (FCFS). A small object can get stuck behind a big one: head-of-line (HOL) blocking. A lost TCP segment also stalls everything.
HTTP/2 (2015)Same methods, status codes and most headers. Sends objects by client-specified priority, not FCFS. Can push unrequested objects. Splits objects into frames and interleaves them to reduce HOL blocking (small objects arrive fast, the big one is only slightly delayed).
HTTP/3HTTP/2 still runs over one TCP connection, so packet loss still stalls every object, and plain TCP has no security. HTTP/3 runs over QUIC over UDP, adding security plus per-object error and congestion control.

QUIC (Quick UDP Internet Connections) is an application-layer protocol on top of UDP. It sets up reliability, congestion control, authentication, encryption and state in one RTT, and multiplexes many streams over one connection.

Quick check

1. DNS visits 3 servers (RTTs 10, 20, 30 ms). RTT₀ = 50 ms. One small HTML object, no transmission time. Total time? $$60 + 2(50) = \mathbf{160 \text{ ms}}$$
2. Same setup, but the HTML references 5 small objects. Non-persistent, no parallel connections? $$60 + 2(50) + 5 \times 2(50) = 60 + 100 + 500 = \mathbf{660 \text{ ms}}$$
3. Same as #2, with 3 parallel connections? \(\lceil 5/3 \rceil = 2\) rounds. $$60 + 100 + 2 \times 100 = \mathbf{360 \text{ ms}}$$
4. Same as #2, persistent with pipelining? Without pipelining? With pipelining: \(60 + 100 + 50 = \mathbf{210 \text{ ms}}\).
Without pipelining: \(60 + 100 + 5 \times 50 = \mathbf{410 \text{ ms}}\).
5. 10 objects, non-persistent, 5 parallel connections, DNS already cached. Answer in RTT₀. \(2\,\text{RTT}_0 + \lceil 10/5 \rceil \times 2\,\text{RTT}_0 = 2 + 4 = \mathbf{6\,\text{RTT}_0}\).
6. Non-persistent, one 1 Mbit object, R = 10 Mbps, RTT = 20 ms. Response time (no DNS)? $$2(20) + \frac{10^6}{10^7} \text{ s} = 40 + 100 = \mathbf{140 \text{ ms}}$$
7. Why does the base HTML still cost 2 RTT with persistent HTTP? The TCP connection doesn't exist yet: 1 RTT to set it up, 1 RTT to request and receive the HTML. Persistence only helps the objects after that.
8. What does "HTTP is stateless" mean, and how do sites remember you anyway? The server keeps no information about past client requests. Sites use cookies: the server sends Set-cookie with an ID, the browser stores it and sends it back in every later request, and the site looks the ID up in its back-end database.
9. What's the difference between 301 and 404? 301 Moved Permanently: the object exists somewhere else (new URL in the Location: header). 404 Not Found: the document isn't on this server.
10. What is HOL blocking, and how does HTTP/2 reduce it? With FCFS, small objects wait behind a large one that was requested first. HTTP/2 splits objects into frames and interleaves them (plus priorities), so small objects get through quickly.
11. Which transport protocol does HTTP/3 use? UDP, through QUIC (which adds reliability, congestion control and security on top).

← 7 · App architectures · all topics · 9 · Web caching →