HTTP/1.1與HTTP/2有什麼區別?
- 2019 年 10 月 16 日
- 筆記
介紹 超文本傳輸協議(HTTP)是一種應用協議,自1989年發明以來,它一直是事實上在萬維網上進行通訊的標準。從1997年發布HTTP / 1.1到最近,對它的修改很少。協議。但是在2015年,重新構想的版本稱為HTTP / 2投入使用,它提供了幾種減少延遲的方法,尤其是在處理移動平台以及伺服器密集型圖形和影片時。此後HTTP / 2變得越來越流行,據估計,世界上約有三分之一的網站都支援HTTP / 2。在這種瞬息萬變的格局中,Web開發人員可以從了解HTTP / 1.1和HTTP / 2之間的技術差異中受益,從而使他們可以就不斷發展的最佳實踐做出明智而有效的決策。 閱讀本文之後,您將了解HTTP / 1.1和HTTP / 2之間的主要區別,重點介紹HTTP / 2為實現更有效的Web協議而採取的技術更改。 ### 背景 為了具體說明HTTP / 2對HTTP / 1.1所做的特定更改,讓我們首先從較高的角度看一下它們的歷史發展和基本工作。 #### HTTP / 1.1 HTTP由Timothy Berners-Lee於1989年開發,作為萬維網的通訊標準,HTTP是一種頂級應用程式協議,它在客戶端電腦與本地或遠程Web伺服器之間交換資訊。在此過程中,客戶端通過調用類似或的方法向伺服器發送基於文本的請求。作為響應,伺服器將HTML頁面之類的資源發送回客戶端。GETPOST 例如,假設您正在訪問域中的網站www.example.com。當您導航到該URL時,電腦上的Web瀏覽器會以基於文本的消息的形式發送HTTP請求,類似於以下所示: “` GET /index.html HTTP/1.1 Host: www.example.com “` 該請求使用的GET方法,該方法從後面列出的主機伺服器中請求數據Host:。響應此請求,example.comWeb伺服器將HTML頁面返回到發出請求的客戶端,此外還包含HTML中要求的任何影像,樣式表或其他資源。請注意,在第一次數據調用中,並非所有資源都會返回給客戶端。請求和響應將在伺服器和客戶端之間來回移動,直到Web瀏覽器收到在螢幕上呈現HTML頁面內容所需的所有資源為止。 您可以將這種請求和響應的交換視為Internet協議棧的單個應用程式層,它位於傳輸層(通常使用傳輸控制協議或TCP)和網路層(使用Internet協議或IP )之上):  關於此堆棧的較低層,有很多要討論的內容,但是為了獲得對HTTP / 2的高層了解,您只需要知道此抽象層模型以及HTTP進入其中的位置即可。 藉助HTTP / 1.1的基本概述,我們現在可以繼續講述HTTP / 2的早期開發。 #### HTTP / 2 HTTP / 2最初是SPDY協議,最初由Google開發,旨在通過使用壓縮,復用和優先順序等技術來減少網頁載入延遲。當[IETF(互聯網工程任務組)](https://www.ietf.org/)的超文本傳輸協議工作組httpbis 將該標準放在一起時,此協議充當HTTP / 2的模板,並最終在2015年5月發布了HTTP / 2。從一開始,許多瀏覽器支援這項標準化工作,包括Chrome,Opera,Internet Explorer和Safari。自2015年以來,部分原因是由於該瀏覽器的支援,該協議的採用率非常高,新站點中的採用率尤其高。 從技術角度來看,區別HTTP / 1.1和HTTP / 2的最重要功能之一是二進位框架層,可以將其視為Internet協議棧中應用程式層的一部分。與HTTP / 1.1(以純文本格式保留所有請求和響應)相反,HTTP / 2使用二進位框架層以二進位格式封裝所有消息,同時仍保持HTTP語義,例如動詞,方法和標頭。應用程式級API仍將以傳統的HTTP格式創建消息,但是基礎層隨後會將這些消息轉換為二進位。這樣可以確保在與新協議進行交互時,在HTTP / 2之前創建的Web應用程式可以繼續正常運行。 將消息轉換為二進位,HTTP / 2可以嘗試HTTP / 1.1中沒有的新的數據傳輸方法,這是兩種協議之間實際差異的根本原因。下一節將介紹HTTP / 1.1的交付模型,然後介紹HTTP / 2帶來了哪些新模型。 ### 投放模式 如上一節所述,HTTP / 1.1和HTTP / 2共享語義,使用熟悉的方法(如GET和),確保在兩種協議之間在伺服器和客戶端之間傳輸的請求和響應作為具有標題和正文的傳統格式的消息到達目的地POST。但是,儘管HTTP / 1.1以純文本消息形式傳輸這些消息,但HTTP / 2卻將它們編碼為二進位,從而提供了截然不同的傳遞模型可能性。在本節中,我們將首先簡要研究HTTP / 1.1如何通過其交付模型來嘗試優化效率以及由此產生的問題,然後是HTTP / 2二進位框架層的優勢以及如何確定優先順序的描述。要求。 #### HTTP / 1.1 —流水線和行頭阻塞 客戶端在HTTP GET請求上收到的第一個響應通常不是完全呈現的頁面。相反,它包含指向所請求頁面所需的其他資源的鏈接。客戶端發現只有在下載頁面後,頁面的完整呈現才需要伺服器提供這些額外資源。因此,客戶端將不得不提出其他請求來檢索這些資源。在HTTP / 1.0中,客戶端必須中斷並重新建立與每個新請求的TCP連接,這在時間和資源上都是一項昂貴的事務。 HTTP / 1.1通過引入持久連接和流水線處理了這個問題。對於持久連接,HTTP / 1.1假定TCP連接應該保持打開狀態,除非直接告知要關閉。這允許客戶端通過同一連接發送多個請求,而不必等待每個請求的響應,從而大大提高了HTTP / 1.1相對於HTTP / 1.0的性能。 不幸的是,這種優化策略存在一個自然的瓶頸。由於多個數據包在到達同一目的地時無法相互傳遞,因此在某些情況下,隊列開頭的無法檢索其所需資源的請求將阻止其後的所有請求。這被稱為行頭(HOL)阻止,並且在優化HTTP / 1.1中的連接效率方面是一個重大問題。添加單獨的並行TCP連接可以緩解此問題,但是客戶端和伺服器之間可能存在的並發TCP連接的數量受到限制,並且每個新連接都需要大量資源。 這些問題在HTTP / 2開發人員的思想中居首位,他們提議使用上述二進位框架層來解決這些問題,您將在下一節中詳細了解該主題。 #### HTTP / 2 —二進位框架層的優點 在HTTP / 2中,二進位幀層對請求/響應進行編碼,並將其切成較小的資訊包,從而大大提高了數據傳輸的靈活性。 讓我們仔細看看它是如何工作的。與HTTP / 1.1(必須使用多個TCP連接來減輕HOL阻塞的影響)相反,HTTP / 2在兩台電腦之間建立了一個連接對象。在此連接內,有多個數據流。每個流由熟悉的請求/響應格式的多個消息組成。最後,每條消息都分成較小的單元,稱為框架:  從最細粒度的角度講,通訊通道由一堆二進位編碼的幀組成,每個幀都標記到特定的流。識別標籤允許連接在傳輸過程中交織這些幀,並在另一端重新組裝它們。交錯的請求和響應可以並行運行,而不會阻塞後面的消息,這一過程稱為multiplexing。通過確保沒有消息等待其他消息完成,多路復用解決了HTTP / 1.1中的行頭阻塞問題。這也意味著伺服器和客戶端可以發送並發請求和響應,從而實現更好的控制和更有效的連接管理。 由於多路復用允許客戶端並行構造多個流,因此這些流僅需要利用單個TCP連接。每個起點只有一個持久連接,可以通過減少整個網路的記憶體和處理佔用空間來改善HTTP / 1.1。這導致更好的網路和頻寬利用率,從而降低了總體運營成本。 單個TCP連接還可以提高HTTPS協議的性能,因為客戶端和伺服器可以將相同的安全會話重用於多個請求/響應。在HTTPS中,在TLS或SSL握手期間,雙方都同意在整個會話過程中使用單個密鑰。如果連接斷開,則新的會話開始,需要新生成的密鑰用於進一步的通訊。因此,維護單個連接可以大大減少HTTPS性能所需的資源。請注意,儘管HTTP / 2規範沒有強制要求使用TLS層,但許多主流瀏覽器僅支援HTTP / 2和HTTPS。 儘管二進位框架層中固有的多路復用解決了HTTP / 1.1的某些問題,但是等待相同資源的多個流仍然會導致性能問題。HTTP / 2的設計考慮了這一點,但是,通過使用流優先順序,我們將在下一節中討論這個主題。 #### HTTP / 2 —流優先順序 流優先順序劃分不僅解決了爭用同一資源的請求的可能問題,而且還允許開發人員自定義請求的相對權重,以更好地優化應用程式性能。在本節中,我們將分解優先順序劃分過程,以便更好地了解如何利用HTTP / 2的此功能。 眾所周知,二進位框架層將消息組織成並行的數據流。當客戶端將並發請求發送到伺服器時,它可以通過為每個流分配1到256之間的權重來區分請求的響應的優先順序。數字越高表示優先順序越高。除此之外,客戶端還通過指定流所依賴的流的ID來聲明每個流對另一流的依賴性。如果省略了父標識符,則認為該流依賴於根流。下圖對此進行了說明:  在圖示中,該頻道包含六個流,每個流具有唯一的ID並與特定的權重關聯。流1沒有與其關聯的父ID,並且默認情況下與根節點關聯。所有其他流都標記了一些父ID。每個流的資源分配將基於它們所擁有的權重及其所需的依賴關係。例如,在圖中已分配了相同權重和相同父流的流5和6,將具有相同的資源分配優先順序。 伺服器使用此資訊來創建依賴關係樹,該依賴關係樹允許伺服器確定請求檢索其數據的順序。根據上圖中的流,依賴關係樹如下:  在此依賴關係樹中,流1依賴於根流,並且沒有其他從根派生的流,因此所有可用資源將在其他流之前分配給流1。由於樹表明流2取決於流1的完成,因此直到流1任務完成,流2才繼續進行。現在,讓我們看一下流3和4。這兩個流都依賴於流2。與流1的情況一樣,流2將獲得流3和4之前的所有可用資源。流2完成其任務後,流3和4將獲得資源;如它們的權重所示,它們按2:4的比例進行分配,從而導致流4的資源更多。最後,當流3完成時,流5和6將獲得相等的可用資源。即使流4接收到更多的資源,這也可能在流4完成其任務之前發生。較高級別的從屬流結束後,就可以開始較低級別的流。 作為應用程式開發人員,您可以根據需要在請求中設置權重。例如,在網頁上提供縮略圖後,可以為較低的優先順序分配高解析度的影像。通過提供這種權重分配功能,HTTP / 2使開發人員可以更好地控制網頁渲染。該協議還允許客戶端響應於用戶交互而在運行時更改依賴關係並重新分配權重。但是,請務必注意,如果某個流被阻止訪問特定資源,則伺服器可以自行更改分配的優先順序。 ### 緩衝區溢出 在兩台機器之間的任何TCP連接中,客戶端和伺服器都有一定數量的緩衝區空間可用於容納尚未處理的傳入請求。除了下游和上游連接的速度不均勻之外,這些緩衝區還提供了靈活性,可以解決眾多或特別大的請求。 但是,在某些情況下,緩衝區不足。例如,由於緩衝區大小有限或頻寬較低,伺服器可能以客戶端應用程式無法應對的速度推送大量數據。同樣,當客戶端將巨大的影像或影片上傳到伺服器時,伺服器緩衝區可能會溢出,從而導致一些其他數據包丟失。 為了避免緩衝區溢出,流控制機制必須防止發送方用數據淹沒接收方。本節將概述HTTP / 1.1和HTTP / 2如何根據其不同的傳遞模型使用此機制的不同版本來處理流控制。 #### HTTP / 1.1 在HTTP / 1.1中,流控制依賴於基礎TCP連接。啟動此連接時,客戶端和伺服器均使用其系統默認設置來建立其緩衝區大小。如果接收方的緩衝區部分填充了數據,它將告訴發送方其接收窗口,即,緩衝區中剩餘的可用空間量。該接收窗口在稱為ACK數據包的訊號中公告,這是接收器發送的數據包,用於確認已接收到打開訊號。如果此公告的接收窗口大小為零,則發送方將不再發送任何數據,直到客戶端清除其內部緩衝區,然後請求恢複數據傳輸為止。在此處需要注意的重要一點是,使用基於基礎TCP連接的接收窗口只能在連接的任一端實現流控制。 因為HTTP / 1.1依賴傳輸層來避免緩衝區溢出,所以每個新的TCP連接都需要單獨的流控制機制。但是,HTTP / 2在單個TCP連接中多路復用流,並且必須以不同的方式實現流控制。 #### HTTP / 2 HTTP / 2在單個TCP連接中多路復用數據流。結果,TCP連接級別的接收窗口不足以調節單個流的傳遞。HTTP / 2通過允許客戶端和伺服器實現自己的流控制,而不是依靠傳輸層來解決此問題。應用程式層傳達可用的緩衝區空間,從而允許客戶端和伺服器在多路復用流的級別上設置接收窗口。在通過WINDOW_UPDATE框架進行初始連接後,可以修改或保持這種精細的流量控制。 由於此方法在應用程式層的級別上控制數據流,因此在調整接收窗口之前,流控制機制不必等待訊號到達其最終目的地。中間節點可以使用流控制設置資訊來確定自己的資源分配並相應地進行修改。這樣,每個中間伺服器都可以實現自己的自定義資源策略,從而提高連接效率。 在創建適當的資源策略時,流控制的這種靈活性可能是有利的。例如,客戶端可以獲取影像的第一次掃描,將其顯示給用戶,並允許用戶預覽影像,同時獲取更多關鍵資源。客戶端獲取這些關鍵資源後,瀏覽器將恢復影像剩餘部分的檢索。因此,將流控制的實現推遲到客戶端和伺服器可以提高Web應用程式的感知性能。 在前面一節中提到的流控制和流優先順序方面,HTTP / 2提供了更詳細的控制級別,為進一步優化提供了可能。下一節將說明該協議特有的另一種方法,該方法可以通過類似的方式增強連接:使用伺服器push預測資源請求。 ### 預測資源請求 在典型的Web應用程式中,客戶端將發送GET請求並接收HTML頁面,通常是網站的索引頁面。在檢查索引頁面內容時,客戶端可能發現它需要獲取其他資源(例如CSS和JavaScript文件)才能完全呈現頁面。客戶端僅在收到其初始GET請求的響應後,才確定需要這些額外的資源,因此客戶端必須提出其他請求以獲取這些資源並完成將頁面放在一起。這些額外的請求最終會增加連接載入時間。 但是,有一些解決方案可以解決此問題:由於伺服器預先知道客戶端將需要其他文件,因此伺服器可以通過在請求這些資源之前將這些資源發送給客戶端來節省客戶端時間。HTTP / 1.1和HTTP / 2具有實現此目的的不同策略,每種策略將在下一節中介紹。 #### HTTP / 1.1 —資源內聯 在HTTP / 1.1中,如果開發人員事先知道客戶端電腦需要呈現頁面的哪些其他資源,則他們可以使用一種稱為資源內聯的技術將所需資源直接包含在伺服器為響應該請求而發送的HTML文檔中。最初的GET要求。例如,如果客戶端需要特定的CSS文件來呈現頁面,則內聯該CSS文件將在客戶端請求之前為客戶端提供所需的資源,從而減少了客戶端必須發送的請求總數。 但是資源內聯存在一些問題。對於較小的基於文本的資源,將資源包括在HTML文檔中是一個可行的解決方案,但是非文本格式的較大文件會大大增加HTML文檔的大小,最終會降低連接速度並抵消最初獲得的優勢使用這項技術。而且,由於內聯資源不再與HTML文檔分開,因此客戶端沒有機制可以拒絕客戶端已經擁有的資源或將資源放入其快取中。如果有多個頁面需要該資源,則每個新HTML文檔的程式碼中都將內聯相同的資源,這導致HTML文檔更大,並且載入時間比起初僅在資源中進行快取的時間長。 因此,資源內聯的主要缺點是客戶端無法分離資源和文檔。需要更好的控制級別來優化連接,HTTP / 2試圖通過伺服器推送來滿足這一需求。 #### HTTP / 2 —伺服器推送 由於HTTP / 2啟用了對客戶端初始GET請求的多個並發響應,因此伺服器可以將資源與請求的HTML頁面一起發送到客戶端,從而在客戶端請求之前提供資源。此過程稱為伺服器推送。這樣,HTTP / 2連接可以實現資源內聯的相同目標,同時保持推送資源與文檔之間的分隔。這意味著客戶端可以決定與主HTML文檔分開快取或拒絕推送的資源,從而解決了資源內聯的主要缺點。 在HTTP / 2中,當伺服器發送一個PUSH_PROMISE幀以通知客戶端它將推送資源時,此過程開始。該幀僅包含消息的標頭,並允許客戶端提前知道伺服器將推送哪個資源。如果已經快取了資源,則客戶端可以通過發送RST_STREAM幀作為響應來拒絕推送。該PUSH_PROMISE框架還可以避免客戶端向伺服器發送重複請求,因為它知道伺服器將要推送的資源。 在此必須注意,伺服器推送的重點是客戶端控制。如果客戶端需要調整伺服器推送的優先順序,甚至禁用它,它可以隨時發送一個SETTINGS幀來修改此HTTP / 2功能。 儘管此功能具有很大的潛力,但伺服器推送並非始終是優化Web應用程式的答案。例如,即使客戶端已經快取了資源,某些Web瀏覽器也無法始終取消推送的請求。如果客戶端錯誤地允許伺服器發送重複資源,則伺服器推送可能會不必要地耗盡連接。最後,伺服器推送應由開發人員自行決定。有關如何從戰略上使用伺服器推送和優化Web應用程式的更多資訊,請查看Google開發的[PRPL模式](https://developers.google.com/web/fundamentals/performance/prpl-pattern/)。要了解有關伺服器推送的可能問題的更多資訊,請參閱Jake Archibald的部落格文章[HTTP / 2 push比我想像的要難](https://jakearchibald.com/2017/h2-push-tougher-than-i-thought/)。 ### 壓縮 優化Web應用程式的常用方法是使用壓縮演算法來減少在客戶端和伺服器之間傳輸的HTTP消息的大小。HTTP / 1.1和HTTP / 2都使用此策略,但是前者中存在實現問題,無法壓縮整個消息。下一節將討論為什麼會這樣,以及HTTP / 2如何提供解決方案。 #### HTTP / 1.1 長期以來,諸如gzip之類的程式一直被用於壓縮HTTP消息中發送的數據,尤其是減小CSS和JavaScript文件的大小。但是,消息的標題部分始終以純文本形式發送。儘管每個標頭都非常小,但是隨著提出更多請求,此未壓縮數據的負擔會越來越重,特別是對複雜,需要大量API且需要許多不同資源請求的Web應用程式造成不利影響。另外,cookie的使用有時會使標頭大得多,從而增加了對某種壓縮的需求。 為了解決此瓶頸,HTTP / 2使用HPACK壓縮來縮小標頭的大小,這一主題將在下一節中進一步討論。 #### HTTP / 2 HTTP / 2中一次又一次出現的主題之一是它使用二進位框架層對更好的細節表現出更大控制的能力。在頭壓縮方面也是如此。HTTP / 2可以從其數據中拆分標頭,從而生成標頭幀和數據幀。然後,特定於HTTP / 2的壓縮程式[HPACK](https://tools.ietf.org/html/draft-ietf-httpbis-header-compression-12)可以壓縮此標頭幀。該演算法可以使用霍夫曼編碼對標頭元數據進行編碼,從而大大減小其大小。此外,HPACK可以跟蹤先前傳送的元數據欄位,並根據客戶端和伺服器之間共享的動態更改的索引進一步壓縮它們。例如,接受以下兩個請求:   在這些請求的各種領域中,如method,scheme,host,accept,和user-agent,具有相同的值; 只有path欄位使用不同的值。結果,在發送時Request #2,客戶端可以使用HPACK僅發送重建這些公共欄位和對該path欄位進行新編碼所需的索引值。結果頭幀將如下所示:   使用HPACK和其他壓縮方法,HTTP / 2提供了另一項功能,可以減少客戶端-伺服器延遲。 ### 結論 從此逐點分析中可以看出,HTTP / 2在許多方面與HTTP / 1.1有所不同,其中一些功能提供了更高級別的控制,可用於更好地優化Web應用程式性能,而其他功能則可以在先前的協議。現在,您已經對這兩種協議之間的變化有了一個高級的了解,現在可以考慮HTTP / 2中的多路復用,流優先順序,流控制,伺服器推送和壓縮等因素如何影響Web開發的不斷變化的格局。 。 如果您希望看到HTTP / 1.1和HTTP / 2之間的性能比較,請查看此[Google演示](https://http2.golang.org/gophertiles),該演示比較了不同延遲的協議。請注意,當您在電腦上運行測試時,頁面載入時間可能會因多種因素而異,例如頻寬,測試時可用的客戶端和伺服器資源,等等。如果您想研究更詳盡的測試結果,請參閱文章[HTTP / 2 –真實的性能測試和分析](https://css-tricks.com/http2-real-world-performance-test-analysis/)。最後,如果您想探索如何構建現代Web應用程式,則可以遵循我們的[《如何構建現代Web應用程式以使用Django和Ubuntu 18.04上的React來管理客戶資訊》](https://www.digitalocean.com/community/tutorials/how-to-build-a-modern-web-application-to-manage-customer-information-with-django-and-react-on-ubuntu-18-04)教程,或使用以下教程方法設置自己的HTTP / 2伺服器[如何在Ubuntu 16.04上使用HTTP / 2支援設置Nginx](https://www.digitalocean.com/community/tutorials/how-to-set-up-nginx-with-http-2-support-on-ubuntu-16-04)。 原文:[HTTP/1.1 vs HTTP/2: What’s the Difference?](https://www.digitalocean.com/community/tutorials/http-1-1-vs-http-2-what-s-the-difference) > 本文由部落格一文多發平台 [OpenWrite](https://openwrite.cn?from=article_bottom) 發布!