成人无码视频,亚洲精品久久久久av无码,午夜精品久久久久久毛片,亚洲 中文字幕 日韩 无码

資訊專欄INFORMATION COLUMN

HTTP/2 技術(shù)調(diào)研和性能分析

hlcfan / 2243人閱讀

摘要:消息與邏輯請(qǐng)求或響應(yīng)消息對(duì)應(yīng)的完整的一系列幀。聲明數(shù)據(jù)流依賴關(guān)系指出,應(yīng)盡可能先向父數(shù)據(jù)流分配資源,然后再向其依賴項(xiàng)分配資源。數(shù)據(jù)流應(yīng)先于和獲得完整資源分配和應(yīng)先于和獲得相同的資源分配和應(yīng)基于其權(quán)重獲得比例分配。

轉(zhuǎn)載自 | 小米運(yùn)維(公眾號(hào) ID:MI-SRE)

HTTP/2 協(xié)議簡(jiǎn)介

HTTP/2 是現(xiàn)行 HTTP 協(xié)議(HTTP/1.x)的替代,但它不是重寫,HTTP 方法 / 狀態(tài)碼 / 語義都與 HTTP/1.x 一樣。不過,HTTP/2 修改了數(shù)據(jù)格式化(分幀)以及在客戶端與服務(wù)器間傳輸?shù)姆绞?。HTTP/2 基于 SPDY3,專注于性能,最大的一個(gè)目標(biāo)是在用戶和網(wǎng)站間只用一個(gè)連接。

HTTP/2 通過支持完整的請(qǐng)求與響應(yīng)復(fù)用來減少延遲,通過有效壓縮 HTTP 報(bào)頭字段將協(xié)議開銷降至最低,同時(shí)增加對(duì)請(qǐng)求優(yōu)先級(jí)和服務(wù)器推送的支持。

HTTP/2 協(xié)議由以下兩個(gè) RFC 組成:

RFC 7540 - Hypertext Transfer Protocol Version 2 (HTTP/2); RFC 7541 -

HPACK: Header Compression for HTTP/2;

HTTP/2 解決的問題

影響一個(gè) HTTP 網(wǎng)絡(luò)請(qǐng)求的因素主要有兩個(gè):帶寬和延遲。在當(dāng)今的網(wǎng)絡(luò)情況下,帶寬一般不再是瓶頸,所以我們主要討論下延遲。延遲一般由下面幾個(gè)因素所造成:

瀏覽器線頭阻塞(Head-Of-Line Blocking):瀏覽器會(huì)因?yàn)橐恍┰蜃枞?qǐng)求。

DNS 查詢。

建立連接(Initial connection):HTTP 基于 TCP 協(xié)議,TCP 的 3 次握手和慢啟動(dòng)極大增加延遲。

HTTP/1.x 中存在的問題

連接無法復(fù)用
連接無法復(fù)用會(huì)導(dǎo)致每次請(qǐng)求都經(jīng)歷三次握手和慢啟動(dòng)。三次握手在高延遲的場(chǎng)景下影響較明顯,慢啟動(dòng)則對(duì)文件類大請(qǐng)求影響較大。

HTTP/1.0 傳輸數(shù)據(jù)時(shí),每次都需要重新建立連接,增加延遲。

HTTP/1.1 雖然加入 keep-alive,可以復(fù)用一部分連接,但域名分片等情況下仍然需要建立多個(gè) connection,耗費(fèi)資源,給服務(wù)器帶來性能壓力。

線頭阻塞(Head-Of-Line Blocking)
導(dǎo)致帶寬無法被充分利用,以及后續(xù)健康請(qǐng)求被阻塞。HOLB 是指在 HTTP/1.x 中,由于服務(wù)器必須按接受請(qǐng)求的順序發(fā)送響應(yīng)的規(guī)則限制,那么假設(shè)瀏覽器在一個(gè)(tcp)連接上發(fā)送了兩個(gè)請(qǐng)求,那么服務(wù)器必須等第一個(gè)請(qǐng)求響應(yīng)完畢才能發(fā)送第二個(gè)響應(yīng)——HOLB。雖然現(xiàn)在瀏覽器允許每個(gè) origin 建立 6 個(gè) connection,但大量網(wǎng)頁(yè)動(dòng)輒幾十個(gè)或上百個(gè)資源,HOLB 依然是主要問題。
協(xié)議開銷大:
HTTP/1.x 中 header 內(nèi)容過大(每次請(qǐng)求 header 基本不怎么變化),增加了傳輸?shù)某杀尽?br>安全因素:
在 HTTP 中傳輸?shù)膬?nèi)容都是明文,客戶端和服務(wù)端雙方無法驗(yàn)證身份。

HTTP/2 解決的問題

連接復(fù)用:
在用戶和網(wǎng)站之間只用一個(gè)連接,避免后續(xù)建立連接過程中的幾個(gè)往返和慢啟動(dòng),同時(shí)減少了服務(wù)器的資源消耗。

沒有線頭阻塞:
采用新的二進(jìn)制分幀層的機(jī)制,組成消息的幀可以亂序發(fā)送,幀到達(dá)對(duì)端重新組裝,不需要等待前面的幀到達(dá)后再發(fā)送。

報(bào)頭壓縮:
HTTP/2 協(xié)議中采用 HPACK 來壓縮請(qǐng)求頭和響應(yīng)頭,降低協(xié)議開銷。

更加安全:
當(dāng)前主流瀏覽器,都只支持基于 HTTPS 部署的 HTTP/2。

HTTP/2 協(xié)議中的新特性 二進(jìn)制分幀層

HTTP 2.0 性能增強(qiáng)的核心,全在于新增的二進(jìn)制分幀層,它定義了如何封裝 HTTP 消息并在客戶端和服務(wù)器之間傳輸,和 HTTP/1.x 對(duì)比如下圖:

這里所謂的 “層”,指的是位于套接字接口與應(yīng)用可見的高級(jí) HTTP API 之間一個(gè)經(jīng)過優(yōu)化的新編碼機(jī)制:HTTP 的語義(包括各種動(dòng)詞、方法、標(biāo)頭)都不受影響,不同的是傳輸期間對(duì)它們的編碼方式變了。HTTP/1.x 協(xié)議以換行符作為純文本的分隔符,而 HTTP/2 將所有傳輸?shù)男畔⒎指顬楦〉南⒑蛶?,并采用二進(jìn)制格式對(duì)它們編碼。
這樣一來,客戶端和服務(wù)器為了相互理解,都必須使用新的二進(jìn)制編碼機(jī)制:HTTP/1.x 客戶端無法理解只支持 HTTP/2 的服務(wù)器,反之亦然。不過不要緊,現(xiàn)有的應(yīng)用不必?fù)?dān)心這些變化,因?yàn)榭蛻舳撕头?wù)器會(huì)替我們完成必要的分幀工作。

數(shù)據(jù)流、消息和幀

新的二進(jìn)制分幀機(jī)制改變了客戶端與服務(wù)器之間交換數(shù)據(jù)的方式。 為了說明這個(gè)過程,我們需要了解 HTTP/2 的三個(gè)概念:

數(shù)據(jù)流:已建立的連接內(nèi)的雙向字節(jié)流,可以承載一條或多條消息。

消息:與邏輯請(qǐng)求或響應(yīng)消息對(duì)應(yīng)的完整的一系列幀。

幀:HTTP/2 通信的最小單位,每個(gè)幀都包含幀頭,至少也會(huì)標(biāo)識(shí)出當(dāng)前幀所屬的數(shù)據(jù)流。

這些概念的關(guān)系總結(jié)如下:

所有通信都在一個(gè) TCP 連接上完成,此連接可以承載任意數(shù)量的雙向數(shù)據(jù)流。

每個(gè)數(shù)據(jù)流都有一個(gè)唯一的標(biāo)識(shí)符和可選的優(yōu)先級(jí)信息,用于承載雙向消息。

每條消息都是一條邏輯 HTTP 消息(例如請(qǐng)求或響應(yīng)),包含一個(gè)或多個(gè)幀。

幀是最小的通信單位,承載著特定類型的數(shù)據(jù),例如 HTTP 標(biāo)頭、消息負(fù)載等等。 來自不同 數(shù)據(jù)流的幀可以交錯(cuò)發(fā)送,然后再根據(jù)每個(gè)幀頭的數(shù)據(jù)流標(biāo)識(shí)符重新組裝,如下圖:

簡(jiǎn)言之,HTTP/2 將 HTTP 協(xié)議通信分解為二進(jìn)制編碼幀的交換,這些幀對(duì)應(yīng)著特定數(shù)據(jù)流中的消息。所有這些都在一個(gè) TCP 連接內(nèi)復(fù)用。這是 HTTP/2 協(xié)議所有其他功能和性能優(yōu)化的基礎(chǔ)。

多路復(fù)用

在 HTTP/1.x 中,如果客戶端要想發(fā)起多個(gè)并行請(qǐng)求以提升性能,則必須使用多個(gè) TCP 連接。這是 HTTP/1.x 交付模型的直接結(jié)果,該模型可以保證每個(gè)連接每次只交付一個(gè)響應(yīng)(響應(yīng)排隊(duì))。更糟糕的是,這種模型也會(huì)導(dǎo)致隊(duì)首阻塞,從而造成底層 TCP 連接的效率低下。
HTTP/2 中新的二進(jìn)制分幀層突破了這些限制,實(shí)現(xiàn)了完整的請(qǐng)求和響應(yīng)復(fù)用:客戶端和服務(wù)器可以將 HTTP 消息分解為互不依賴的幀,然后交錯(cuò)發(fā)送,最后再在另一端把它們重新組裝起來。

上圖捕捉了同一個(gè)連接內(nèi)并行的多個(gè)數(shù)據(jù)流??蛻舳苏谙蚍?wù)器傳輸一個(gè) DATA 幀(數(shù)據(jù)流 5),與此同時(shí),服務(wù)器正向客戶端交錯(cuò)發(fā)送數(shù)據(jù)流 1 和數(shù)據(jù)流 3 的一系列幀。因此,一個(gè)連接上同時(shí)有三個(gè)并行數(shù)據(jù)流。
將 HTTP 消息分解為獨(dú)立的幀,交錯(cuò)發(fā)送,然后在另一端重新組裝是 HTTP 2 最重要的一項(xiàng)增強(qiáng)。事實(shí)上,這個(gè)機(jī)制會(huì)在整個(gè)網(wǎng)絡(luò)技術(shù)棧中引發(fā)一系列連鎖反應(yīng),從而帶來巨大的性能提升,讓我們可以:

并行交錯(cuò)地發(fā)送多個(gè)請(qǐng)求,請(qǐng)求之間互不影響。

并行交錯(cuò)地發(fā)送多個(gè)響應(yīng),響應(yīng)之間互不干擾。

使用一個(gè)連接并行發(fā)送多個(gè)請(qǐng)求和響應(yīng)。

不必再為繞過 HTTP/1.x 限制而做很多工作(對(duì) HTTP/1.x 進(jìn)行優(yōu)化,例如級(jí)聯(lián)文件、image sprites 和域名分片。

消除不必要的延遲和提高現(xiàn)有網(wǎng)絡(luò)容量的利用率,從而減少頁(yè)面加載時(shí)間。

等等…

HTTP/2 中的新二進(jìn)制分幀層解決了 HTTP/1.x 中存在的隊(duì)首阻塞問題,也消除了并行處理和發(fā)送請(qǐng)求及響應(yīng)時(shí)對(duì)多個(gè)連接的依賴。結(jié)果,應(yīng)用速度更快、開發(fā)更簡(jiǎn)單、部署成本更低。

請(qǐng)求重置

HTTP 1.1 的有一個(gè)缺點(diǎn)是:當(dāng)一個(gè)含有確切值的 Content-Length 的 HTTP 消息被送出之后,你就很難中斷它了。當(dāng)然,通常你可以斷開整個(gè) TCP 連接(但也不總是可以這樣),但這樣導(dǎo)致的代價(jià)就是需要通過三次握手來重新建立一個(gè)新的 TCP 連接。
一個(gè)更好的方案是只終止當(dāng)前傳輸?shù)南⒉⒅匦掳l(fā)送一個(gè)新的。在 HTTP/2 里面,我們可以通過發(fā)送 RST_STREAM 幀來實(shí)現(xiàn)這種需求,從而避免浪費(fèi)帶寬和中斷已有的連接。

請(qǐng)求優(yōu)先級(jí)

將 HTTP 消息分解為很多獨(dú)立的幀之后,我們就可以復(fù)用多個(gè)數(shù)據(jù)流中的幀,客戶端和服務(wù)器交錯(cuò)發(fā)送和傳輸這些幀的順序就成為關(guān)鍵的性能決定因素。為了做到這一點(diǎn),HTTP/2 標(biāo)準(zhǔn)允許每個(gè)數(shù)據(jù)流都有一個(gè)關(guān)聯(lián)的權(quán)重和依賴關(guān)系:

可以向每個(gè)數(shù)據(jù)流分配一個(gè)介于 1 至 256 之間的整數(shù)。

每個(gè)數(shù)據(jù)流與其他數(shù)據(jù)流之間可以存在顯式依賴關(guān)系。

數(shù)據(jù)流依賴關(guān)系和權(quán)重的組合讓客戶端可以構(gòu)建和傳遞 “優(yōu)先級(jí)樹”,表明它傾向于如何接收響應(yīng)。反過來,服務(wù)器可以使用此信息通過控制 CPU、內(nèi)存和其他資源的分配設(shè)定數(shù)據(jù)流處理的優(yōu)先級(jí),在資源數(shù)據(jù)可用之后,帶寬分配可以確保將高優(yōu)先級(jí)響應(yīng)以最優(yōu)方式傳輸至客戶端。

如上圖,HTTP/2 內(nèi)的數(shù)據(jù)流依賴關(guān)系通過將另一個(gè)數(shù)據(jù)流的唯一標(biāo)識(shí)符作為父項(xiàng)引用進(jìn)行聲明;如果忽略標(biāo)識(shí)符,相應(yīng)數(shù)據(jù)流將依賴于 “根數(shù)據(jù)流”。聲明數(shù)據(jù)流依賴關(guān)系指出,應(yīng)盡可能先向父數(shù)據(jù)流分配資源,然后再向其依賴項(xiàng)分配資源。換句話說,“請(qǐng)先處理和傳輸響應(yīng) D,然后再處理和傳輸響應(yīng) C”。

共享相同父項(xiàng)的數(shù)據(jù)流(即,同級(jí)數(shù)據(jù)流)應(yīng)按其權(quán)重比例分配資源。 例如,如果數(shù)據(jù)流 A 的權(quán)重為 12,其同級(jí)數(shù)據(jù)流 B 的權(quán)重為 4,那么要確定每個(gè)數(shù)據(jù)流應(yīng)接收的資源比例,請(qǐng)執(zhí)行以下操作:
將所有權(quán)重求和:4 + 12 = 16
將每個(gè)數(shù)據(jù)流權(quán)重除以總權(quán)重:A = 12/16, B = 4/16 因此,數(shù)據(jù)流 A 應(yīng)獲得四分之三的可用資源,數(shù)據(jù)流 B 應(yīng)獲得四分之一的可用資源;數(shù)據(jù)流 B 獲得的資源是數(shù)據(jù)流 A 所獲資源的三分之一。 我們來看一下上圖中的其他幾個(gè)動(dòng)手示例:順序?yàn)閺淖蟮接遥?/p>

   數(shù)據(jù)流 A 和數(shù)據(jù)流 B 都沒有指定父依賴項(xiàng),依賴于顯式 “根數(shù)據(jù)流”;A 的權(quán)重為 12,B 的權(quán)重為 4。因此,根據(jù)比例權(quán)重:數(shù)據(jù)流 B 獲得的資源是 A 所獲資源的三分之一。
   數(shù)據(jù)流 D 依賴于根數(shù)據(jù)流;C 依賴于 D。因此,D 應(yīng)先于 C 獲得完整資源分配。權(quán)重不重要,因?yàn)?C 的依賴關(guān)系擁有更高的優(yōu)先級(jí)。
   數(shù)據(jù)流 D 應(yīng)先于 C 獲得完整資源分配;C 應(yīng)先于 A 和 B 獲得完整資源分配;數(shù)據(jù)流 B 獲得的資源是 A 所獲資源的三分之一。
   數(shù)據(jù)流 D 應(yīng)先于 E 和 C 獲得完整資源分配;E 和 C 應(yīng)先于 A 和 B 獲得相同的資源分配;A 和 B 應(yīng)基于其權(quán)重獲得比例分配。

如上面的示例所示,數(shù)據(jù)流依賴關(guān)系和權(quán)重的組合明確表達(dá)了資源優(yōu)先級(jí),這是一種用于提升瀏覽性能的關(guān)鍵功能,網(wǎng)絡(luò)中擁有多種資源類型,它們的依賴關(guān)系和權(quán)重各不相同。不僅如此,HTTP/2 協(xié)議還允許客戶端隨時(shí)更新這些優(yōu)先級(jí),進(jìn)一步優(yōu)化了瀏覽器性能。換句話說,我們可以根據(jù)用戶互動(dòng)和其他信號(hào)更改依賴關(guān)系和重新分配權(quán)重。

注:數(shù)據(jù)流依賴關(guān)系和權(quán)重表示傳輸優(yōu)先級(jí),而不是要求,因此不能保證特定的處理或傳輸順序。即,客戶端無法強(qiáng)制服務(wù)器通過數(shù)據(jù)流優(yōu)先級(jí)以特定順序處理數(shù)據(jù)流。 盡管這看起來違反直覺,但卻是一種必要行為。 我們不希望在優(yōu)先級(jí)較高的資源受到阻止時(shí),還阻止服務(wù)器處理優(yōu)先級(jí)較低的資源。

每個(gè)來源一個(gè)連接

有了新的分幀機(jī)制后,HTTP/2 不再依賴多個(gè) TCP 連接去并行復(fù)用數(shù)據(jù)流;每個(gè)數(shù)據(jù)流都拆分成很多幀,而這些幀可以交錯(cuò),還可以分別設(shè)定優(yōu)先級(jí)。因此,所有 HTTP/2 連接都是永久的,而且僅需要每個(gè)來源一個(gè)連接,隨之帶來諸多性能優(yōu)勢(shì)。
大多數(shù) HTTP 傳輸都是短暫且急促的,而 TCP 則針對(duì)長(zhǎng)時(shí)間的批量數(shù)據(jù)傳輸進(jìn)行了優(yōu)化。 通過重用相同的連接,HTTP/2 既可以更有效地利用每個(gè) TCP 連接,也可以顯著降低整體協(xié)議開銷。不僅如此,使用更少的連接還可以減少占用的內(nèi)存和處理空間,也可以縮短完整連接路徑(即,客戶端、可信中介和源服務(wù)器之間的路徑)這降低了整體運(yùn)行成本并提高了網(wǎng)絡(luò)利用率和容量。 因此,遷移到 HTTP/2 不僅可以減少網(wǎng)絡(luò)延遲,還有助于提高通量和降低運(yùn)行成本。

在 HTTP/2 RFC 文檔中建議實(shí)現(xiàn)時(shí)客戶端不應(yīng)該在給定的目的地上打開多個(gè) HTTP/2 連接,目的地是由給定的 URI 確定的 IP 地址及 TCP 端口,或者配置的代理 IP 和端口。當(dāng)然客戶端可以使用不相同的服務(wù)端名稱標(biāo)識(shí)值或者提供不一樣的 ssl 證書對(duì)相同的 IP 地址及 TCP 端口打開多個(gè)連接,但應(yīng)該避免對(duì)相同的配置上創(chuàng)建多個(gè)連接。
注:連接數(shù)量減少對(duì)提升 HTTPS 部署的性能來說是一項(xiàng)特別重要的功能:可以減少開銷較大的 TLS 連接數(shù)、提升會(huì)話重用率,以及從整體上減少所需的客戶端和服務(wù)器資源。

流量控制

流量控制是一種阻止發(fā)送方向接收方發(fā)送大量數(shù)據(jù)的機(jī)制,以免超出后者的需求或處理能力:發(fā)送方可能非常繁忙、處于較高的負(fù)載之下,也可能僅僅希望為特定數(shù)據(jù)流分配固定量的資源。例如,客戶端可能請(qǐng)求了一個(gè)具有較高優(yōu)先級(jí)的大型視頻流,但是用戶已經(jīng)暫停視頻,客戶端現(xiàn)在希望暫停或限制從服務(wù)器的傳輸,以免提取和緩沖不必要的數(shù)據(jù)。再比如,一個(gè)代理服務(wù)器可能具有較快的下游連接和較慢的上游連接,并且也希望調(diào)節(jié)下游連接傳輸數(shù)據(jù)的速度以匹配上游連接的速度來控制其資源利用率;等等。

不過,由于 HTTP/2 數(shù)據(jù)流在一個(gè) TCP 連接內(nèi)復(fù)用,TCP 流控制既不夠精細(xì),也無法提供必要的應(yīng)用級(jí) API 來調(diào)節(jié)各個(gè)數(shù)據(jù)流的傳輸。為了解決這一問題,HTTP/2 提供了一組簡(jiǎn)單的構(gòu)建塊,這些構(gòu)建塊允許客戶端和服務(wù)器實(shí)現(xiàn)其自己的數(shù)據(jù)流和連接級(jí)流量控制:

流量控制具有方向性,每個(gè)接收方都可以根據(jù)自身需要選擇為每個(gè)數(shù)據(jù)流和整個(gè)連接設(shè)置任意的窗口大小。

流量控制基于窗口更新幀進(jìn)行,即接收方廣播自己準(zhǔn)備接收某個(gè)數(shù)據(jù)流的多少字節(jié),以及對(duì)整個(gè)連接要接收多少字節(jié)。

流量控制窗口大小通過 WINDOW_UPDATE 幀更新,這個(gè)字段制定了流 ID 和窗口遞增值。

流量控制可以由接收方禁用,包括針對(duì)個(gè)別的流和針對(duì)整個(gè)連接。

流量控制基于每一跳進(jìn)行,而非端到端控制。即,可信中介可以使用它來控制資源使用,以及基于自身?xiàng)l件和啟發(fā)式算法實(shí)現(xiàn)資源分配機(jī)制。

HTTP/2 未指定任何特定算法來實(shí)現(xiàn)流量控制。不過,它提供了簡(jiǎn)單的構(gòu)建塊并推遲了客戶端和服務(wù)器實(shí)現(xiàn),可以實(shí)現(xiàn)自定義策略來調(diào)節(jié)資源使用和分配,以及實(shí)現(xiàn)新傳輸能力,同時(shí)提升網(wǎng)絡(luò)應(yīng)用的實(shí)際性能和感知性能。

例如,應(yīng)用層流量控制允許瀏覽器僅提取一部分特定資源,通過將數(shù)據(jù)流流控制窗口減小為零來暫停提取,稍后再行恢復(fù)。換句話說,它允許瀏覽器提取圖像預(yù)覽或首次掃描結(jié)果,進(jìn)行顯示并允許其他高優(yōu)先級(jí)提取繼續(xù),然后在更關(guān)鍵的資源完成加載后恢復(fù)提取。

服務(wù)器推送

HTTP/2 新增的另一個(gè)強(qiáng)大的新功能是,服務(wù)器可以對(duì)一個(gè)客戶端請(qǐng)求發(fā)送多個(gè)響應(yīng)。 換句話說,除了對(duì)最初請(qǐng)求的響應(yīng)外,服務(wù)器還可以向客戶端推送額外資源(如下圖),而無需客戶端明確地請(qǐng)求。

注:HTTP/2 打破了嚴(yán)格的請(qǐng)求 - 響應(yīng)語義,支持一對(duì)多和服務(wù)器發(fā)起的推送工作流,在瀏覽器內(nèi)外開啟了全新的互動(dòng)可能性。這是一項(xiàng)使能功能,對(duì)我們思考協(xié)議、協(xié)議用途和使用方式具有重要的長(zhǎng)期影響。

為什么在瀏覽器中需要一種此類機(jī)制呢?一個(gè)典型的網(wǎng)絡(luò)應(yīng)用包含多種資源,客戶端需要檢查服務(wù)器提供的文檔才能逐個(gè)找到它們。那為什么不讓服務(wù)器提前推送這些資源,從而減少額外的延遲時(shí)間呢?服務(wù)器已經(jīng)知道客戶端下一步要請(qǐng)求什么資源,這時(shí)候服務(wù)器推送即可派上用場(chǎng)。

事實(shí)上,如果在網(wǎng)頁(yè)中內(nèi)聯(lián)過 CSS、JavaScript,或者通過數(shù)據(jù) URI 內(nèi)聯(lián)過其他資產(chǎn),那么就已經(jīng)親身體驗(yàn)過服務(wù)器推送了。對(duì)于將資源手動(dòng)內(nèi)聯(lián)到文檔中的過程,我們實(shí)際上是在將資源推送給客戶端,而不是等待客戶端請(qǐng)求。使用 HTTP/2,我們不僅可以實(shí)現(xiàn)相同結(jié)果,還會(huì)獲得其他性能優(yōu)勢(shì)。 推送資源可以進(jìn)行以下處理:

由客戶端緩存

在不同頁(yè)面之間重用

與其他資源一起復(fù)用

由服務(wù)器設(shè)定優(yōu)先級(jí)

被客戶端拒絕

PUSH_PROMISE 101

所有服務(wù)器推送數(shù)據(jù)流都由 PUSH_PROMISE 幀發(fā)起,表明了服務(wù)器向客戶端推送所述資源的意圖,并且需要先于請(qǐng)求推送資源的響應(yīng)數(shù)據(jù)傳輸。這種傳輸順序非常重要:客戶端需要了解服務(wù)器打算推送哪些資源,以免為這些資源創(chuàng)建重復(fù)請(qǐng)求。滿足此要求的最簡(jiǎn)單策略是先于父響應(yīng)(即,DATA 幀)發(fā)送所有 PUSH_PROMISE 幀,其中包含所承諾資源的 HTTP 標(biāo)頭。
在客戶端接收到 PUSH_PROMISE 幀后,它可以根據(jù)自身情況選擇拒絕數(shù)據(jù)流(通過 RST_STREAM 幀)。 (如果資源已經(jīng)位于緩存中,可能會(huì)發(fā)生這種情況。) 這是一個(gè)相對(duì)于 HTTP/1.x 的重要提升。 相比之下,使用資源內(nèi)聯(lián)(一種受歡迎的 HTTP/1.x“優(yōu)化”)等同于 “強(qiáng)制推送”:客戶端無法選擇拒絕、取消或多帶帶處理內(nèi)聯(lián)的資源。
使用 HTTP/2,客戶端仍然完全掌控服務(wù)器推送的使用方式。客戶端可以限制并行推送的數(shù)據(jù)流數(shù)量;調(diào)整初始的流控制窗口以控制在數(shù)據(jù)流首次打開時(shí)推送的數(shù)據(jù)量;或完全停用服務(wù)器推送。這些優(yōu)先級(jí)在 HTTP/2 連接開始時(shí)通過 SETTINGS 幀傳輸,可能隨時(shí)更新。
推送的每個(gè)資源都是一個(gè)數(shù)據(jù)流,與內(nèi)嵌資源不同,客戶端可以對(duì)推送的資源逐一復(fù)用、設(shè)定優(yōu)先級(jí)和處理。 瀏覽器強(qiáng)制執(zhí)行的唯一安全限制是,推送的資源必須符合原點(diǎn)相同這一政策:服務(wù)器對(duì)所提供內(nèi)容必須具有權(quán)威性。

報(bào)頭壓縮

每個(gè) HTTP 傳輸都承載一組報(bào)頭,這些報(bào)頭說明了傳輸?shù)馁Y源及其屬性。 在 HTTP/1.x 中,此元數(shù)據(jù)始終以純文本形式,通常會(huì)給每個(gè)傳輸增加 500–800 字節(jié)的開銷。如果使用 HTTP Cookie,增加的開銷有時(shí)會(huì)達(dá)到上千字節(jié)。為了減少此開銷和提升性能, HTTP/2 使用 HPACK 壓縮格式壓縮請(qǐng)求和響應(yīng)標(biāo)頭元數(shù)據(jù),這種格式采用兩種簡(jiǎn)單但是強(qiáng)大的技術(shù):

這種格式支持通過靜態(tài) Huffman 編碼對(duì)傳輸?shù)臉?biāo)頭字段進(jìn)行編碼,從而減小了各個(gè)傳輸?shù)拇笮 ?/p>

這種格式要求客戶端和服務(wù)器同時(shí)維護(hù)和更新一個(gè)包含之前見過的標(biāo)頭字段的索引列表(換句話說,它可以建立一個(gè)共享的壓縮上下文),此列表隨后會(huì)用作參考,對(duì)之前傳輸?shù)闹颠M(jìn)行有效編碼。

利用 Huffman 編碼,可以在傳輸時(shí)對(duì)各個(gè)值進(jìn)行壓縮,而利用之前傳輸值的索引列表,我們可以通過傳輸索引值的方式對(duì)重復(fù)值進(jìn)行編碼,索引值可用于有效查詢和重構(gòu)完整的標(biāo)頭鍵值對(duì)。

作為一種進(jìn)一步優(yōu)化方式,HPACK 壓縮上下文包含一個(gè)靜態(tài)表和一個(gè)動(dòng)態(tài)表:靜態(tài)表在規(guī)范中定義,并提供了一個(gè)包含所有連接都可能使用的常用 HTTP 標(biāo)頭字段(例如,有效標(biāo)頭名稱)的列表;動(dòng)態(tài)表最初為空,將根據(jù)在特定連接內(nèi)交換的值進(jìn)行更新。因此,為之前未見過的值采用靜態(tài) Huffman 編碼,并替換每一側(cè)靜態(tài)表或動(dòng)態(tài)表中已存在值的索引,可以減小每個(gè)請(qǐng)求的大小。
注:在 HTTP/2 中,請(qǐng)求和響應(yīng)標(biāo)頭字段的定義保持不變,僅有一些微小的差異:所有標(biāo)頭字段名稱均為小寫,請(qǐng)求行現(xiàn)在拆分成各個(gè) :method、:scheme、:authority 和 :path 偽標(biāo)頭字段。

至于 HPACK 壓縮的詳細(xì)介紹,請(qǐng)點(diǎn)擊這里:HTTP/2 頭部壓縮技術(shù)介紹或者官方 RFC。

HTTP/2 協(xié)議實(shí)際性能測(cè)試與分析

為了測(cè)試 HTTP/2 對(duì) web 訪問的性能提升,本人借助 bbs 產(chǎn)品線的 miui 官方網(wǎng)站,開啟了 tengine 的 HTTP/2 的支持,取一周的訪問數(shù)據(jù)與 HTTPS、HTTP 訪問數(shù)據(jù)進(jìn)行對(duì)比分析,詳細(xì)結(jié)果如下:

采集數(shù)據(jù)量

響應(yīng)類型分布

請(qǐng)求類別 http https http2
2xx 945144 927482 505702
3xx 243075 258331 681997
4xx 2372 4750 2813
5xx 9 37 88
sum 1190600 1190600 1190600
延遲數(shù)據(jù)分析

2xx 請(qǐng)求各個(gè)響應(yīng)時(shí)間段占比(基于 nginx log 的 request_time 數(shù)據(jù))

時(shí)間 http https http2
<50ms 79.75% 78.89% 82.60%
<100ms 87.24% 87.47% 89.86%
<150ms 91.12% 91.90% 93.19%
<200ms 92.72% 93.82% 94.54%
<2s 98.99% 99.71% 99.48%

2xx 請(qǐng)求響應(yīng)時(shí)間大于 7 秒的數(shù)量 (基于 nginx log 的 request_time 數(shù)據(jù))

時(shí)間 http https http2
>7s 1960(0.207%) 603(0.065%) 950(0.187%)
>10s 1519(0.160%) 420(0.045%) 638(0.126%)
>30s 594(0.062%) 165(0.017%) 190(0.037%)
>60s 259(0.027%) 104(0.011%) 97(0.019%)

2xx 請(qǐng)求后端響應(yīng)時(shí)間超過 7 秒的數(shù)量(基于 nginx log 的 upstream_response_time)

時(shí)間 http https http2
>7s 68(0.007%) 88(0.017%) 58(0.006%)
帶寬數(shù)據(jù)分析

301 請(qǐng)求響應(yīng)大?。ɑ?nginx 的 request_length 和 bytes_sent 數(shù)據(jù))

/static/image/common/miui9.jpg 請(qǐng)求數(shù) 總大小(byte) avg(byte) 請(qǐng)求總大小(byte) 請(qǐng)求avg(byte)
http 2722 1460146 536 3194589 1173
https 4695 2618278 415 8019924 1708
http2 16239 6751609 557 1209570 74

200 請(qǐng)求響應(yīng)大小(基于 nginx log 的 request_length 和 bytes_sent 數(shù)據(jù))

/favicon.ico 請(qǐng)求數(shù) 響應(yīng)總大小(byte) 響應(yīng)avg(byte) 請(qǐng)求總大小(byte) 請(qǐng)求avg(byte)
http 17658 23552229 1413 15300656 866
https 117178 165623779 1413 122356406 1044
http2 80856 105496656 1304 10015908 123
來源分析

客戶端分析(基于 nginx log 的 user_agent 數(shù)據(jù))

協(xié)議 chrome MSIE safari FireFox Crawlers others unknown
http 23.53% 4.26% 3.56% 0.67% 4.01% 15.07% 48.22%
https 79.24% 5.93% 3.67% 1.54% 7.87% 1.42% 0.1%
http2 88.57% 4.93% 1.91% 1.57% 0% 2.9% 0.03%

平臺(tái)分析(基于 nginx log 的 user_agent 數(shù)據(jù))

協(xié)議 Android Windows Linux IOS Darwin unknown
http 28.4% 16.07% 0.29% 2.46% 0.12% 51.86%
https 64.85% 24.65% 0.62% 0.54% 0.29% 9.05%
http2 40.06% 57.62% 1.49% 0.44% 0% 0.02%
結(jié)論

典型網(wǎng)絡(luò) RTT 下(50~200ms),HTTP/2 對(duì)網(wǎng)絡(luò)延遲性能有一定程度的提升,優(yōu)于 HTTP/1.x 和 HTTPS。

在 2xx 和 3xx 請(qǐng)求下 HTTP/2 利用 HPACK 機(jī)制壓縮響應(yīng)頭和請(qǐng)求頭,有效降低了請(qǐng)求和響應(yīng)的大小,節(jié)省了流量,降低了協(xié)議消耗。

目前 HTTP/2 大部分流量來自于 chrome,其對(duì) HTTP/2 的支持性也是最好的。

HTTP/2 協(xié)議部署建議 建議一:現(xiàn)在是否需要遷移到 HTTP/2

實(shí)現(xiàn) HTTP/2 很簡(jiǎn)單,不過,HTTP/2 并不是萬能的銀彈,它只對(duì)某些 Web 應(yīng)用有用,對(duì)另外一些則沒那么有用。

如果你使用 SSL/TLS(以后簡(jiǎn)稱 TLS),那么 HTTP/2 可以提升網(wǎng)站性能。如果你沒有,那在使用 HTTP/2 之前要先支持 TLS。這時(shí)候,使用 TLS 的性能損耗大致可以被使用 HTTP/2 的性能提升抵銷。不過還是建議你在實(shí)際應(yīng)用之前先測(cè)試一下。
HTTP/2 有五大優(yōu)勢(shì):

每個(gè)服務(wù)器只用一個(gè)連接。HTTP/2 對(duì)每個(gè)服務(wù)器只使用一個(gè)連接,而不是每個(gè)文件一個(gè)連接。這樣,就省掉了多次建立連接的時(shí)間,這個(gè)時(shí)間對(duì) TLS 尤其明顯,因?yàn)?TLS 連接費(fèi)時(shí)間。

加速 TLS 交付。HTTP/2 只需一次耗時(shí)的 TLS 握手,并且通過一個(gè)連接上的多路利用實(shí)現(xiàn)最佳性能。HTTP/2 還會(huì)壓縮首部數(shù)據(jù),省掉 HTTP/1.x 時(shí)代所需的一些優(yōu)化工作,比如拼接文件,從而提高緩存利用率。

簡(jiǎn)化 Web 應(yīng)用。使用 HTTP/2 可以讓 Web 開發(fā)者省很多事,因?yàn)椴挥迷僮瞿切┽槍?duì) HTTP/1.x 的優(yōu)化工作了。

適合內(nèi)容混雜的頁(yè)面。HTTP/2 特別適合混合了 HTML、CSS、JavaScript、圖片和有限多媒體的傳統(tǒng)頁(yè)面。瀏覽器可以優(yōu)先安排那些重要的文件請(qǐng)求,讓頁(yè)面的關(guān)鍵部分先出現(xiàn),快出現(xiàn)。

更安全。通過減少 TLS 的性能損失,可以讓更多應(yīng)用使用 TLS,從而讓用戶信息更安全。

相應(yīng)地,HTTP/2 也有五個(gè)不足之處。

單連接開銷比較大。HPACK 數(shù)據(jù)壓縮算法會(huì)更新兩端的查找表。這樣可以讓連接有狀態(tài),而破壞狀態(tài)就意味著要重建查找表,另外單連接占用內(nèi)存較多。

你可能不需要 SSL。如果你的數(shù)據(jù)不需要保護(hù),或者已經(jīng)使用 DRM 或其他編碼進(jìn)行保護(hù)了,那么 TLS 的安全性對(duì)你可能無所謂。

需要拋棄針對(duì) HTTP/1.x 的優(yōu)化。HTTP/1.x 優(yōu)化在支持 HTTP/2 的瀏覽器中會(huì)影響性能,因此可能需要花時(shí)間把它們推倒重來。

對(duì)下載大文件不利。如果你的應(yīng)用主要提供大文件下載或者流媒體播放,那可能不想用 TLS,而且在只有一個(gè)流的情況下,多路復(fù)用也體現(xiàn)不出什么優(yōu)勢(shì)。

你的客戶也許不在乎。你的客戶很可能不在乎他分享的自家貓咪的視頻是否受到 TLS 和 HTTP/2 的保護(hù)。

總之,一切要看性能。這方面,有好消息也有壞消息。
好消息是 nginx 官方團(tuán)隊(duì)在內(nèi)部對(duì) NGINX 做過測(cè)試,結(jié)果從理論上能夠得到印證:對(duì)于要通過典型網(wǎng)絡(luò)延遲請(qǐng)求的混合內(nèi)容網(wǎng)頁(yè),HTTP/2 的性能好于 HTTP/1.x 和 HTTPS?;谶B接的 RTT,結(jié)果可以分三種情況。

很低的 RTT(0-20ms):HTTP/1.x、HTTP/2 和 HTTPS 基本無差別。

典型網(wǎng)絡(luò) RTT(30-250ms):HTTP/2 比 HTTP/1.x 快,而且它們都比 HTTPS 快。美國(guó)兩個(gè)相鄰城市間的 RTT 約為 30 ms,而東西海岸間(約 3000 英里)則約為 70 ms。東京到倫敦間最短路徑的 RTT 大約 240 ms。

高 RTT(300ms 及以上):HTTP/1.x 比 HTTP/2 快,后者又比 HTTPS 快。

這張圖顯示了首次渲染的時(shí)間,也就是用戶第一次在自己屏幕上看到網(wǎng)頁(yè)內(nèi)容的時(shí)間。這個(gè)時(shí)間一般認(rèn)為關(guān)系到用戶對(duì)網(wǎng)站響應(yīng)速度的感知。

然而,每個(gè)網(wǎng)頁(yè)都不相同,實(shí)際上每個(gè)用戶的會(huì)話也不一樣。如果你托管流媒體或提供大文件下載,那你的決定可能不一樣,甚至相反。

建議二:終止 HTTP/2 和 TLS

終止協(xié)議意味著客戶端使用期望的協(xié)議連接代理服務(wù)器,比如 TLS 或 HTTP/2,然后代理服務(wù)器再去連接應(yīng)用服務(wù)器、數(shù)據(jù)庫(kù)服務(wù)器等,但不需要使用相同的協(xié)議,如下圖所示。

使用獨(dú)立的服務(wù)器終止協(xié)議意味著使用多服務(wù)器架構(gòu)。多服務(wù)器可能是多個(gè)物理服務(wù)器、多個(gè)虛擬服務(wù)器,或者 AWS 這樣的云環(huán)境中的多個(gè)虛擬服務(wù)器實(shí)例。多服務(wù)器就比單服務(wù)器復(fù)雜,或者比應(yīng)用服務(wù)器 / 數(shù)據(jù)庫(kù)服務(wù)器的組合復(fù)雜。不過,多服務(wù)器架構(gòu)有很多好處,而且很多流量大的網(wǎng)站也必須用這種架構(gòu)。

配置了服務(wù)器或者虛擬服務(wù)器之后,很多事情都成為可能。新服務(wù)器可以分擔(dān)其他服務(wù)器的負(fù)載,可用于負(fù)載平衡、靜態(tài)文件緩存和其他用途。另外,也可以讓添加和替換應(yīng)用服務(wù)器或其他服務(wù)器更容易。
NGINX 和 NGINX Plus 經(jīng)常被用來終止 TLS 和 HTTP/2 協(xié)議、負(fù)載平衡。已有環(huán)境不必改動(dòng),除非要把 NGINX 服務(wù)器挪到前端。

建議三:找出為 HTTP/1.x 優(yōu)化的代碼

在決定采用 HTTP/2 之前,首先得知道你的代碼有哪些是針對(duì) HTTP/1.x 優(yōu)化過的。大概有四方面的優(yōu)化。

分域存儲(chǔ)。為了實(shí)現(xiàn)并行請(qǐng)求文件,你可能把文件分散到了不同的域里,CDN 會(huì)自動(dòng)這么做。但分域存儲(chǔ)會(huì)影響 HTTP/2 的性能,建議使用 HTTP/2 友好的分域存儲(chǔ)(建議六),只針對(duì) HTTP/1.x 用戶分域。

雪碧圖。雪碧圖把很多圖片拼成一個(gè)文件,然后通過代碼按需取得每個(gè)圖片。雪碧圖在 HTTP/2 的環(huán)境下沒太大用處,但還是有點(diǎn)用的。

拼接的代碼文件。與使用雪碧圖的原因類似,很多獨(dú)立的文件也會(huì)被弄成一個(gè),然后瀏覽器再?gòu)钠渲姓业讲⑦\(yùn)行需要的文件。

插入行內(nèi)的文件。CSS 代碼、JavaScript 代碼,甚至圖片等被直接插到 HTML 文件中的內(nèi)容。這樣可以減少文件傳輸,代價(jià)是初始 HTML 文件較大。

后面三種優(yōu)化都涉及把小文件塞進(jìn)一個(gè)較大的文件里,目的是減少新建連接的初始化和握手,這些操作對(duì) TLS 而言非常費(fèi)時(shí)間。

第一種優(yōu)化即分域存儲(chǔ)恰恰相反,強(qiáng)制打開多個(gè)連接,目的是并行地從不同的域獲取文件。這兩種看似矛盾的技術(shù)對(duì)于 HTTP/1.x 下的站點(diǎn)卻十分有效。然而,要用好這兩種技術(shù),必須投入大量時(shí)間、精力和資源,用于實(shí)現(xiàn)、管理和運(yùn)維。

在采用 HTTP/2 之前,需要找出應(yīng)用了這些優(yōu)化的代碼,分析一下它們會(huì)不會(huì)影響你的應(yīng)用設(shè)計(jì)和工作流程。這樣在遷移到 HTTP/2 之后,就可以著手改造它們,甚至撤銷某些優(yōu)化。

建議四:部署 HTTP/2

事實(shí)上,部署 HTTP/2 并不難。如果使用 NGINX,只要在配置文件中啟動(dòng)相應(yīng)的協(xié)議就可以了。瀏覽器和服務(wù)器會(huì)協(xié)商采用什么協(xié)議,如果瀏覽器支持 HTTP/2(而且也在使用 TLS),就會(huì)使用 HTTP/2。
配置完服務(wù)器后,使用支持 HTTP/2 瀏覽器的用戶就會(huì)基于 HTTP/2 運(yùn)行你的應(yīng)用,而使用舊版本瀏覽器的用戶則會(huì)繼續(xù)使用 HTTP/1.x 運(yùn)行你的應(yīng)用,如下圖所示。如果你的網(wǎng)站流量非常大,那么應(yīng)該監(jiān)測(cè)改變前后的性能,對(duì)于性能降低的情況,可能就得撤銷更改。

注意:使用 HTTP/2 及其單連接之后,NGINX 某些配置的重要性會(huì)很明顯,特別要注意的是 output_buffers、proxy_buffers 和 ssl_buffer_size 等指令,多測(cè)試一下。參見 general configuration notes,特定的 SSL 建議,以及 NGINX 關(guān)于 SSL 性能的白皮書。
注意:使用 HTTP/2 傳輸密文要格外注意。HTTP/2 的 RFC 中有一個(gè)長(zhǎng)長(zhǎng)的列表,列出了要避免的加密套件。建議你自己也搞一個(gè)表格,啟用 ssl_buffer_size,然后在所有常用的瀏覽器版本下測(cè)試你想用的加密套件。

建議五:再談 HTTP/1.x 優(yōu)化

你說奇怪不,撤銷和修改針對(duì) HTTP/1.x 優(yōu)化的代碼居然是實(shí)現(xiàn) HTTP/2 最有創(chuàng)意的部分。這里面有幾個(gè)問題要注意,因?yàn)楹芏嗍略趺醋龆际强梢缘摹?br>在開始運(yùn)作之前,必須考慮舊版本瀏覽器用戶是否好過。之后,可以采取三個(gè)策略撤銷和修改 HTTP/1.x 的優(yōu)化。

什么也不用做。假如你并沒有針對(duì) HTTP/1.x 做過優(yōu)化,或者只做過少量?jī)?yōu)化,那么你幾乎什么也不用做,就可以直接遷移到 HTTP/2。

有選擇地去做。第二種情況是減少合并某些文件,而不是完全不合并。比如,牽扯到很多場(chǎng)景的雪碧圖就不用動(dòng),而被塞得滿滿的 HTML 可能就要分離出來一些。

完全撤銷 HTTP/1.x 優(yōu)化。可以不再做以前做過的任何優(yōu)化。

緩存還是普適的。理論上,緩存操作非常適合小文件特別多的情況。但是,小文件多也意味著文件 I/O 多。因此一些相近文件的合并還是必要的,一方面要考慮工作流程,另一方面要考慮應(yīng)用性能。建議多關(guān)注一下其他人在過渡到 HTTP/2 過程中的一些經(jīng)驗(yàn)。

建議六:實(shí)現(xiàn)智能分域

分域存儲(chǔ)可能是最極端但也最成功的 HTTP/1.x 優(yōu)化策略。它能夠提升 HTTP/1.x 下的應(yīng)用性能,但在 HTTP/2 之下,其性能提升可以忽略不講(因?yàn)橹挥幸粋€(gè)連接。)
對(duì) HTTP/2 友好的分域,要保證以下兩點(diǎn):

讓多個(gè)域名解析到同一個(gè) IP。

確保證書包含通配符,以便所有分域名都可以使用,適當(dāng)?shù)亩嘤蜃C書當(dāng)然也可以。

有了這些保障,分域還會(huì)繼續(xù)對(duì) HTTP/1.x 有效,即域名仍然可以觸發(fā)瀏覽器創(chuàng)建更多連接,但對(duì) HTTP/2 則無效,因?yàn)檫@些域名會(huì)被看成同一個(gè)域,一個(gè)連接就可以訪問所有域名了。

HTTP/2 協(xié)議客戶端和服務(wù)支持情況 客戶端

PC 端

如果業(yè)務(wù)提供的是 web 形式的內(nèi)容,通過瀏覽器進(jìn)行訪問,由于當(dāng)前大部分的瀏覽器都已經(jīng)支持 HTTP/2 了,所以基本不需進(jìn)行任何操作,以下為支持 HTTP/2 的瀏覽器列表:

瀏覽器 支持HTTP/2 基于的內(nèi)核 備注
Chrome(49) 支持 從49版本開始支持
IE 11 不支持 win10系統(tǒng)上的IE11支持h2
Edge(14) 支持 從14版本開始支持
Safari(10.1) 支持 從10.1版本開始支持,但都需要OSX10.11+以上系統(tǒng)版本
Firefox(52) 支持 從52版本開始支持
Opera(47.0.2631.55) 支持 從46版本開始支持
搜狗瀏覽器(7.1.5.25209) 支持
獵豹瀏覽器(6.0.114.15532) 支持
2345加速瀏覽器(8.7.0.16013) 支持
百度瀏覽器(8.7.5000.4962) 不支持 chrome 47
QQ瀏覽器(9.6.4) 支持 chrome 53
360瀏覽器(9.1.0.346) 支持 chrome 55
360極速瀏覽器(8.7.0.306) 支持

移動(dòng)端

安卓 app 基本采用 JAVA 開發(fā),由于各個(gè)應(yīng)用采用的與服務(wù)端通信的 http 庫(kù)各不相同,有的是采用 jdk 自帶的 httpurlconnection 庫(kù)和 httpclient 庫(kù),有的用的是安卓系統(tǒng)自帶的 webview 或者 volley(volley 的 HTTP/2 支持依賴于所使用的 httpstack,默認(rèn)使用 httpurlconection,但現(xiàn)在也有很多開發(fā)者使用第三方的 okhttp 作為 volley 的 httpstack),而有的開發(fā)者直接使用的是第三方庫(kù)類似于 okhttp,netty 等,這些 http 庫(kù)對(duì) http2.0 的支持情況各不相同。

基于 java 開發(fā)的 http 庫(kù)對(duì) HTTP/2 的支持情況如下:

Jetty 從 9.3 版本開始支持,需要依賴于 JDK 8 及以上版本

Netty 從 4.1 版本開始支持

OkHttp 天然支持

Vert.xh 從 3.3.0 版本開始支持

Firefly 支持

其它

Golang 的 net/http 庫(kù)從 Go1.6 版本開始支持 http2,并默認(rèn)開啟

服務(wù)端
名稱 支持的版本 支持的協(xié)商機(jī)制
Apache HTTP Server 2.4.17+ h2,h2c ALPN,Upgrade,direct
Apache Tomcat 8.5+ h2,h2c ALPN,Upgrade,direct
Nginx h2,h2c ALPN,NPN,direct
Tengine 2.1.2+ h2 ALPN
Twisted h2 NPN,ALPN
Netty h2,h2c ALPN,NPN,Upgrade,direct

在 HTTP/2 的 github 中維護(hù)了一份 HTTP/2 協(xié)議的實(shí)現(xiàn)列表,更加詳細(xì),可供參考。

擴(kuò)展閱讀 1.NPN 和 ALPN

由于現(xiàn)有的 URI 結(jié)構(gòu)正在被 HTTP 1.x 使用而不能被更換,所以 HTTP/2 也必須沿用該結(jié)構(gòu)。因此不得不找到一種方式將使用的協(xié)議升級(jí)至 HTTP/2,比如可以要求服務(wù)器讓它作響應(yīng)時(shí)使用 HTTP/2 來替代舊的協(xié)議。

HTTP 1.1 本身就制定過 “升級(jí)” 的方案:提供一個(gè)首部字段,表示允許服務(wù)器在收到舊協(xié)議請(qǐng)求的同時(shí),可以向客戶端發(fā)送新協(xié)議的響應(yīng)。但這一方案往往需要花費(fèi)一次額外的往返通信來作為升級(jí)的代價(jià)。
而這一代價(jià)是 SPDY 團(tuán)隊(duì)不想接受的。因?yàn)樗麄冎粚?shí)現(xiàn)了基于 TLS 的 SPDY,所以他們開發(fā)了一個(gè) TLS 的擴(kuò)展去簡(jiǎn)化協(xié)議的協(xié)商。這個(gè)擴(kuò)展被稱作 NPN(Next Protocol Negotiation),借助于此,服務(wù)器會(huì)通知客戶端所有它支持的協(xié)議,讓客戶端從中選擇一個(gè)合適的來進(jìn)行通訊。

IETF 將這個(gè)非正式標(biāo)準(zhǔn) --NPN 進(jìn)行規(guī)范化,從而演變成了 ALPN(Application Layer Protocol Negotiation)。ALPN 會(huì)隨著 HTTP/2 的應(yīng)用被推廣,而 SPDY 的客戶端與服務(wù)器則會(huì)繼續(xù)使用 NPN。
由于 NPN 先于 ALPN 誕生,而 ALPN 又經(jīng)歷了一些標(biāo)準(zhǔn)化過程,所以許多早期的 HTTP/2 客戶端和服務(wù)器在協(xié)商 HTTP/2 時(shí)會(huì)將這兩者同時(shí)實(shí)現(xiàn)。與此同時(shí),考慮到 SPDY 會(huì)使用 NPN,而許多服務(wù)器又會(huì)同時(shí)提供 SPDY 以及 HTTP/2,所以在這些服務(wù)器上同時(shí)支持 ALPN 以及 NPN 顯然會(huì)成為最理所當(dāng)然的選擇。
ALPN 和 NPN 的主要區(qū)別在于:誰來決定通信協(xié)議。在 ALPN 的描述中,是讓客戶端先發(fā)送一個(gè)協(xié)議優(yōu)先級(jí)列表給服務(wù)器,由服務(wù)器最終選擇一個(gè)合適的。而 NPN 則正好相反,客戶端有著最終的決定權(quán)。

ALPN 擴(kuò)展的具體資料,可以參考 Jerry Qu 寫的這篇博客:談?wù)?HTTP/2 的協(xié)議協(xié)商機(jī)制

2.QUIC

QUIC (Quick UDP Internet Connection,快速 UDP 互聯(lián)網(wǎng)連接) 是一個(gè)新的基于 UDP 的多路復(fù)用且安全的傳輸協(xié)議,它從頭開始設(shè)計(jì),且為 HTTP/2 語義做了優(yōu)化。盡管以 HTTP/2 作為主要的應(yīng)用協(xié)議而構(gòu)建,然而 QUIC 的構(gòu)建是基于傳輸和安全領(lǐng)域數(shù)十年的經(jīng)驗(yàn)的,且實(shí)現(xiàn)了使它成為有吸引力的現(xiàn)代通用傳輸協(xié)議的機(jī)制。QUIC 提供了等價(jià)于
HTTP/2 的多路復(fù)用和流控,等價(jià)于 TLS 的安全機(jī)制,及等價(jià)于 TCP 的連接語義、可靠性和擁塞控制。

QUIC 完全運(yùn)行于用戶空間,它當(dāng)前作為 Chromium 瀏覽器的一部分發(fā)布給用戶,以便于快速的部署和實(shí)驗(yàn)。作為基于 UDP 的用戶空間傳輸協(xié)議,QUIC 可以做一些由于遺留的客戶端和中間設(shè)備,或曠日持久的操作系統(tǒng)開發(fā)和部署周期的阻礙,而被證明很難在現(xiàn)有的協(xié)議中部署的創(chuàng)新。

QUIC 的一個(gè)重要目標(biāo)是通過快速的實(shí)驗(yàn)獲得更好的傳輸設(shè)計(jì)相關(guān)的知識(shí)。

基于早期的部署的 QUIC 標(biāo)準(zhǔn)化建議為 [draft-hamilton-quic-transport-protocol],[draft-shade-quic-http2-mapping],[draft-iyengar-quic-loss-recovery],和 [draft-thomson-quic-tls]。

更加詳細(xì)的資料請(qǐng)參考這里:中文文檔; Chromium 的 QUIC 主頁(yè)。

參考資料

web 性能權(quán)威指南

HTTP/2 RFC 文檔

HTTP/2 explained

Nginx HTTP/2 白皮書

HTTP/2 is here, let"s optimize! - Velocity SC 2015

Jerry Qu 的小站 - HTTP/2 資料匯總

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://m.hztianpu.com/yun/8049.html

相關(guān)文章

  • 微服務(wù)網(wǎng)關(guān)方案調(diào)研

    摘要:綜述經(jīng)調(diào)研,使用解決方案的占多數(shù),已經(jīng)能滿足絕大多數(shù)公司需求。但除了一些超級(jí)公司外,比如阿里,京東,他們是自己擼的一套網(wǎng)關(guān)。 綜述 經(jīng)調(diào)研,使用Spring Cloud Zuul解決方案的占多數(shù),已經(jīng)能滿足絕大多數(shù)公司需求。但除了一些超級(jí)公司外,比如阿里,京東,他們是自己擼的一套網(wǎng)關(guān)。此外,點(diǎn)評(píng)直接采用的nginx負(fù)載均衡前置網(wǎng)關(guān),而沒用第七層網(wǎng)關(guān),原因據(jù)說是七層網(wǎng)關(guān)會(huì)影響性能,但由于...

    Y3G 評(píng)論0 收藏0
  • 《云計(jì)算技術(shù)與應(yīng)用》的社會(huì)需求調(diào)研報(bào)告

    摘要:一國(guó)外云計(jì)算技術(shù)的發(fā)展隨著世界各國(guó)對(duì)云計(jì)算的大力投入,以及行業(yè)內(nèi)技術(shù)的快速發(fā)展,現(xiàn)階段整個(gè)產(chǎn)業(yè)公司均在進(jìn)行云計(jì)算的產(chǎn)業(yè)整合。由第三方統(tǒng)計(jì)機(jī)構(gòu)提供的數(shù)據(jù)顯示,與云計(jì)算相關(guān)的業(yè)務(wù)收入已達(dá)億美元,成為增長(zhǎng)最快的業(yè)務(wù)之一。云計(jì)算(cloud computing)技術(shù)是上世紀(jì)八十年代大型計(jì)算機(jī)到客戶端-服務(wù)器的大轉(zhuǎn)變之后的又一種巨變。隨著通信技術(shù)、網(wǎng)絡(luò)技術(shù)的快速發(fā)展,云計(jì)算被視為科技發(fā)展的下一次革命,...

    0x584a 評(píng)論0 收藏0
  • CNCF權(quán)威調(diào)研揭示K8s用戶所面臨的最大挑戰(zhàn)

    摘要:然而此次調(diào)研結(jié)果表明,企業(yè)采用時(shí)面臨的挑戰(zhàn)中,復(fù)雜性僅排在第五位,用戶面臨的基礎(chǔ)設(shè)施相關(guān)的挑戰(zhàn)更大。在監(jiān)控方面,中型組織更可能會(huì)面臨挑戰(zhàn)。 人們?cè)谑褂眉安渴餕ubernetes時(shí)會(huì)遇到各種各樣的問題。一些挑戰(zhàn)是使用Kubernetes時(shí)獨(dú)有的,其他一些挑戰(zhàn)則是伴隨著一些技術(shù)的使用出現(xiàn)的典型問題。 The New Stack發(fā)布的《Kubernetes的生態(tài)系統(tǒng)狀況》報(bào)告總結(jié)了用戶在挑...

    wpw 評(píng)論0 收藏0
  • 互聯(lián)網(wǎng)公司的完整開發(fā)流程是怎樣的?

    摘要:一前言對(duì)于很多還沒進(jìn)入社會(huì)或者之前沒有在互聯(lián)網(wǎng)公司呆過的人來說,會(huì)很好奇互聯(lián)網(wǎng)企業(yè)的開發(fā)流程是怎樣的,正好借著我最近這段時(shí)間的經(jīng)歷寫下這一篇介紹開發(fā)流程的文章。整體的開發(fā)流程涉及到的人員角色有項(xiàng)目經(jīng)理產(chǎn)品設(shè)計(jì)后端開發(fā)前端開發(fā)運(yùn)維測(cè)試。 ...

    Coding01 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

hlcfan

|高級(jí)講師

TA的文章

閱讀更多
最新活動(dòng)
閱讀需要支付1元查看
<