[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

江米小棗tonylua發表於2018-05-10

HTTP 的進化 - 理解真實的 HTTP 是如何工作的

原文: https://medium.com/platform-engineer/evolution-of-http-69cfe6531ba0


自從在 1989-1991 年間被 CERN(譯註:即“歐洲核子研究組織”的原稱 - Conseil Européen pour la Recherche Nucléaire)的 Tim Berners-Lee 發明出來以後,HTTP(超文字傳輸協議) 就一直是全球資訊網的基礎傳輸協議。在 C/S 計算模型中,HTTP 起到了一個“請求/響應”協議的作用。HTTP 標準由 IETF(因特網工程任務組) 和 W3C(全球資訊網聯盟)負責開發,並以一系列註釋請求(RFCs - Requests for Comments)的形式被髮布。HTTP 有 4 個版本:HTTP/0.9、HTTP/1.0、HTTP/1.1 以及 HTTP/2.0。當前通常使用 HTTP/1.1 版本,未來會是 HTTP/2.0。

HTTP/0.9 — 單行協議

  • HTTP 的首個版本 — 一個簡單的 客戶端/伺服器、請求/響應、對 telenet 友好的協議
  • 請求: 單行 (method + 所請求文件的 path)
  • 支援的方法: 僅 GET
  • 響應型別: 僅 超文字
  • 響應後馬上結束的連線
  • 沒有 HTTP headers (無法傳輸其他內容型別的檔案), 沒有 status/error 程式碼, 沒有 URLs, 沒有版本控制
$> telnet ashenlive.com 80

(連線1建立 - TCP 三次握手)
Connected to xxx.xxx.xxx.xxx

(請求)
GET /my-page.html

(超文字響應)
<HTML>
A very simple HTML page
</HTML>

(連線1關閉 - 斷掉 TCP)
複製程式碼

流行的 web 伺服器(Apache, Nginx)始終支援 HTTP/0.9。可以開啟一個 Telnet 會話訪問 google.com 試試。

HTTP/1.0 — 構建可擴充套件性

  • 對瀏覽器友好的協議
  • 提供了對請求和響應都包含豐富後設資料的 header 域 (HTTP 版本號、status code 和 content type)
  • 響應:不再只限於超文字 (Content-Type 頭部提供了傳輸 HTML 之外檔案的能力 — 如指令碼、樣式或媒體檔案)
  • 支援的方法: GET , HEAD , POST
  • 響應後馬上結束的連線
(連線1建立 - TCP 三次握手)
Connected to xxx.xxx.xxx.xxx

(請求)
GET /my-page.html HTTP/1.0 
User-Agent: NCSA_Mosaic/2.0 (Windows 3.1)

(響應)
HTTP/1.0 200 OK 
Content-Type: text/html 
Content-Length: 137582
Expires: Thu, 01 Dec 1997 16:00:00 GMT
Last-Modified: Wed, 1 May 1996 12:45:26 GMT
Server: Apache 0.84

<HTML> 
A page with an image
  <IMG SRC="/myimage.gif">
</HTML>

(連線1關閉 - 斷掉 TCP)

------------------------------------------

(連線2建立 - TCP 三次握手)
Connected to xxx.xxx.xxx.xxx

(請求)
GET /myimage.gif HTTP/1.0
User-Agent: NCSA_Mosaic/2.0 (Windows 3.1)

(響應)
HTTP/1.0 200 OK 
Content-Type: text/gif 
Content-Length: 137582
Expires: Thu, 01 Dec 1997 16:00:00 GMT
Last-Modified: Wed, 1 May 1996 12:45:26 GMT
Server: Apache 0.84

[image content]

(連線2關閉 - 斷掉 TCP)
複製程式碼

HTTP/0.9 和 HTTP/1.0 的主要問題 — 為每個請求建立一個新連線

HTTP/0.9 和 HTTP/1.0 都需要為每次請求建立一個新的連線(並在收到對應的響應後立即關閉該連線)。每次新連線建立時,都要經歷一遍 TCP 三次握手。考慮到更好的效能,應該著重減少這些 C/S 之間的往返通訊。HTTP/1.1 用持久化連線解決了這個問題。

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

典型的 TCP 三次握手(觀察一下 TCP 狀態機是如何改變其狀態的吧)

HTTP/1.1 — 標準化的協議

  • 這是當前普遍使用的 HTTP 版本
  • 進行了重大的效能優化和特性增強,分塊傳輸、壓縮/解壓、內容快取磋商、虛擬主機(有單個 IP 地址的主機具有多個域名)、更快的響應,以及通過增加快取節省了更多的頻寬
  • 支援的方法: GET , HEAD , POST , PUT , DELETE , TRACE , OPTIONS
  • 長久的連線
(連線1建立 - TCP 三次握手)
Connected to xxx.xxx.xxx.xxx

(請求1)
GET /en-US/docs/Glossary/Simple_header HTTP/1.1
Host: developer.mozilla.org
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.9; rv:50.0) Gecko/20100101 Firefox/50.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate, br
Referer: https://developer.mozilla.org/en-US/docs/Glossary/Simple_header

(響應1)
HTTP/1.1 200 OK
Connection: Keep-Alive
Content-Encoding: gzip
Content-Type: text/html; charset=utf-8
Date: Wed, 20 Jul 2016 10:55:30 GMT
Etag: "547fa7e369ef56031dd3bff2ace9fc0832eb251a"
Keep-Alive: timeout=5, max=1000
Last-Modified: Tue, 19 Jul 2016 00:59:33 GMT
Server: Apache
Transfer-Encoding: chunked
Vary: Cookie, Accept-Encoding

[content]

(請求2)
GET /static/img/header-background.png HTTP/1.1
Host: developer.cdn.mozilla.net
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.9; rv:50.0) Gecko/20100101 Firefox/50.0
Accept: */*
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate, br
Referer: https://developer.mozilla.org/en-US/docs/Glossary/Simple_header

(響應2)
HTTP/1.1 200 OK
Age: 9578461
Cache-Control: public, max-age=315360000
Connection: keep-alive
Content-Length: 3077
Content-Type: image/png
Date: Thu, 31 Mar 2016 13:34:46 GMT
Last-Modified: Wed, 21 Oct 2015 18:27:50 GMT
Server: Apache

[image content of 3077 bytes]

(連線1關閉 - 斷掉 TCP)
複製程式碼

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

TCP 三次握手會在任何連線被建立之前發生一次。最終,當傳送了所有資料之後,伺服器傳送一個訊息,表示不會再有更多資料向客戶端傳送了;則客戶端才會關閉連線(斷開 TCP)。HTTP/1.0 存在的問題是,對於每個 請求/響應 輪迴,也要建立並關閉一個連線。而改用 HTTP/1.1 後的優點則在於,可以複用同一個連線,來完成多次 請求/響應 輪迴

Keep-Alive 和 Upgrade 頭部

Keep-Alive 頭部

  • Connection: Keep-Alive 頭部在 HTTP/1.1 之前就存在,但在 HTTP/1.1 中該頭部被廢棄了,因為持久化連線變成了預設的行為(譯註:除非用Connection: Close顯式關閉)。Keep-Alive 頭部可以被用於在主機之間定義持久連線通訊策略(比如使一個連線在某個事件發生之前都保持啟用)。這奠定了持久化、連線複用、管道化及其他很多現代 web 通訊協議中被加強能力的基礎。
  • 可以對客戶端、伺服器,或任何中間人分別設定獨立的 Keep-Alive 頭部。同時,主機可以增加 timeout 引數以設定一個超時,或用 max 引數限制每個連線的最大請求數。
HTTP/1.1 200 OK
Connection: Keep-Alive
Content-Encoding: gzip
Content-Type: text/html; charset=utf-8
Date: Thu, 11 Aug 2016 15:23:13 GMT
Keep-Alive: timeout=5, max=1000
Last-Modified: Mon, 25 Jul 2016 04:32:39 GMT
Server: Apache

[body] 
複製程式碼

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

`Keep-Alive` 頭部的用法。所有連線都是獨立協商的
  • 受益於 Keep-Alive 頭部,HTTP 管道化實現了多個連線,以及其他更多改進。

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

HTTP 管道化和多個並行連線

Upgrade 頭部

  • 藉助 HTTP/1.1 帶來的 Upgrade 頭部,便可用一個常用的協議起步,比如 HTTP/1.1,然後讓該連線切換到增強的協議型別,如 HTTP/2.0 或 WebSockets。
  • 在一個升級過的連線中,不再有 max 引數了。升級後的協議為 timeout 引數提供了新的策略(如果沒有特別定義,使用基礎協議預設的 timeout 值)。

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

由 HTTP/1.1 升級到 WebSocket[RFC6455]

HTTPS

  • 加密超文字傳輸協議(HTTPS)是 HTTP 的安全版本,使用 SSL/TLS 完成安全加密通訊。
  • 最初由網景公司在 90 年代中期開發,SSL(安全套接字層)是一種增強 HTTP 的密碼學協議,定義了客戶端和伺服器之間如何安全的互相通訊。TLS(安全傳輸層協議)是 SSL 的繼承者。
  • 因為在客戶端和伺服器間提供了雙向加密,HTTPS 連線可以在資料傳輸中防止中間人攻擊和常見的安全威脅。

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

訪問 msdn.microsoft.com 站點時的 SSL 握手過程 — TCP 連線 -> SSL/TLS 客戶端 Hello -> SSL/TLS 伺服器 Hello -> SSL/TLS 認證 -> SSL/TLS 客戶端交換祕鑰 -> SSL/TLS 新會話 Ticket -> HTTPS 加密資料傳輸

SSL/TLS 握手 — HTTPS 中的主要問題

  • 儘管 HTTPS 設計上是安全的,但 SSL/TLS 握手過程在 HTTPS 連線之前消耗了顯著的時間;通常會耗費 1 至 2 秒,極大影響了網站啟動效能。

HTTP/2.0 和未來

所有以上提及的特性,當今都已經被主要的伺服器和瀏覽器所使用了。但像 HTTP/2.0、Server Side Events (SSE) 以及 WebSocket 這樣的現代增強功能,則改變了傳統 HTTP 的工作方式。

參考:

  1. https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Evolution_of_HTTP
  2. https://tools.ietf.org/id/draft-thomson-hybi-http-timeout-01.html
  3. https://developer.mozilla.org/en-US/docs/Web/HTTP/Protocol_upgrade_mechanism
  4. https://hpbn.co/brief-history-of-http/
----------------------------------------

長按二維碼或搜尋 fewelife 關注我們哦

[譯] HTTP 的進化 - 0.9、1.0、1.1、Keep-Alive、Upgrade 和 HTTPS

相關文章