更智能的HTTP/2(HTTP/2: Smarter at scale)

https://www.cncf.io/blog/2018/07/03/http-2-smarter-at-scale/安全

發佈於2018-07-03服務器

本篇博客的做者爲:Jean de Klerk, 谷歌公司的程序開發工程師網絡

當前大部分網頁都基於HTTP/1.1 協議。HTTP/1.1 協議的規則發表於1999年6月,距今小20年了; 儘管發生瞭如此大的變化,HTTP/1.1延用至今並蓬勃發展,真是讓人注目;但在一些領域,她仍是略顯老態,由於HTTP/1.1並非爲其處理當前如此大規模和大流量的應用而設計的併發

HTTP/2協議規範發表於2015年5月,解決了其前身HTTP/1.1 的可擴展問題並提供了相似的使用體驗;HTTP/2在幾個方面對HTTP/1.1進行了改進,最重要的改進是在鏈接上提供了語義映射。在本文中咱們將探討流的概念,以及它給軟件工程師帶來的實際幫助;負載均衡

鏈接的語義映射

建立一個HTTP鏈接的開銷很大,你必須建立一個TCP鏈接,使用TLS保證鏈接的安全,交換HTTP的header和settings數據,等;HTTP/1.1爲了簡化這一流程,加長了鏈接的生命週期,並將鏈接看做一個可重用的對象。HTTP/1.1的鏈接保持空閒,當新的、一樣目的地的請示到來時就能夠複用已存在且空閒的鏈接;雖然複用鏈接緩解了這個問題,但一個鏈接一次只能處理一個請示,它們是1:1耦合的。若是一個大消息在發送,新的請示必須等待它發送結束,這就致使了行道阻塞(head-of-line blocking),或者,大部分狀況下,咱們須要建立另外一個鏈接;框架

HTTP/2經過在鏈接之上提供一個語義層:流,來加強持久鏈接;流能夠被認爲是一系列語義上的消息,這些消息稱爲幀;一個流的生命週期可能很短,像請示用戶狀態的一元流,在HTTP/1.1中,相似於 GET /users/1234/status,當請示頻率增長,其生命週期變長; 在這種狀況下,客戶端可能會創建一個長期存在的流,這樣就能夠持續的,實時的獲取用戶的狀態;性能

https://s3-us-west-2.amazonaws.com/secure.notion-static.com/2632f670-2b78-42bf-9f65-d729febca87f/Untitled.png

流提供的併發性

流提供的主要優勢是鏈接的併發性,如,鏈接上交錯處理消息的能力;spa

爲了解釋這一點,咱們想像這樣一個場景;幾個A服務向服務B發送HTTP/1.1 請求來建立用戶,更新我的資料信息,建立產品訂單;產品訂單比較大,每個訂單都會分爲5個TCP包;簡況更新很小,只須要一個TCP包;用記建立請示也很小須要兩個TCP包;設計

在某個時間段快照中,服務A有一個空閒的鏈接須要向服務B發送數據;服務A須要發送一個產品訂單(request 1), 一個我的資料更新(request 2) 和兩個建立用戶請求(request 3, 4)。由於產品訂單請求先到,request 1便佔據了空閒的鏈接,其他的三個請示要麼等待產品訂單完成發送,要麼建立一些新的HTTP/1.1鏈接.代理

https://s3-us-west-2.amazonaws.com/secure.notion-static.com/719dec9e-9c77-450d-99ca-e1495b859e75/Untitled.png

同時,使用HTTP / 2,流技術容許在同一鏈接上同時發送消息。 假設服務A建立了與服務B的鏈接,該鏈接有三個流:「新用戶」流,「我的資料更新」流和「產品訂單」流。 如今,後一個請求沒必要等待第一個到達的大型產品訂單請求; 全部請求同時發送。

可是,併發並不意味着並行。 咱們一次只能發送一個數據包。 所以,發送方可能會輪流在流之間循環發送數據包(請參見下文)。 或者,發送者能夠將某些流優先於其餘流。 也許讓新用戶註冊對該服務更重要!

https://s3-us-west-2.amazonaws.com/secure.notion-static.com/7435f72a-d669-46df-876e-6a41c4db1e4f/Untitled.png

流量控制

可是,併發流包含一些微妙的陷阱。 請考慮如下狀況:同一鏈接上的兩個流A和B。 流A接收大量數據,遠遠超出了短期內能夠處理的數據量。 最終,接收者的緩衝區已滿,而且TCP接收窗口限制了發送者。 對於TCP,這都是至關標準的行爲,可是這種狀況對於流來講是不利的,由於這兩個流都不會接收更多數據。 理想狀況下,流B應該不受流A緩慢處理的影響。

HTTP / 2經過提供流量控制機制做爲流規範的一部分來解決此問題。 流量控制用於限制每一個流(和每一個鏈接)的未完成數據量。 它做爲一種信用系統運行,接收方分配必定的「預算」,而發送方「支出」該預算。 更具體地說,接收方分配一些緩衝區大小(「預算」),發送方經過發送數據來填充(「支出」)緩衝區。接收方使用專用的WINDOW_UPDATE幀向發送方通告其餘可用的緩衝區(在可用時)。 當接收方中止播發額外的緩衝區時,發送方必須在緩衝區(其「預算」)用盡時中止發送消息。

使用流量控制,能夠確保併發流獨立分配緩衝區。 結合循環請求發送,能夠在單個鏈接上多路複用全部大小,處理速度和持續時間的流,而沒必要擔憂跨流問題。

智能代理

HTTP / 2的併發屬性使代理的性能更高。 例如,考慮一個HTTP / 1.1負載均衡器,它接受並轉發尖峯流量:當出現尖峯時,代理啓動更多鏈接以處理負載或將請求排隊。 前者(新鏈接)一般(在某種程度上)是首選; 這些新鏈接的缺點不只在於等待系統調用和套接字的時間,還在於在TCP慢啓動發生時未充分利用鏈接所花費的時間。

相反,考慮配置爲每一個鏈接多路複用100個流的HTTP / 2代理。 必定數量的請求峯值仍將致使新的鏈接被啓動,可是與HTTP / 1.1須要的鏈接數相比,只須要其1/100的鏈接數。 更籠統地說:若是n個HTTP / 1.1請求發送到代理,則n個HTTP / 1.1請求必須發送出去; 每一個請求都是單個有意義的數據請求/有效負載,而且鏈接的請求爲1:1。 相反,對於HTTP / 2,發送到代理的n個請求須要n個流,可是並不須要n個鏈接!

代理具備進行各類智能干預的空間,如:

  • 測量其自身與服務之間的帶寬延遲積(BDP),而後透明地建立支持傳入流所需的最小鏈接數
  • 在不影響基礎鏈接的狀況下殺死空閒流
  • 跨鏈接的負載平衡流,在這些鏈接之間平均分配流量,確保最大程度地利用鏈接
  • 基於WINDOW_UPDATE幀來衡量處理速度,並使用加權負載平衡來區分從消息處理速度更快的流發送消息的優先級。

https://s3-us-west-2.amazonaws.com/secure.notion-static.com/adcfb922-631c-4f26-8a66-33450474b10a/Untitled.png

更智能的HTTP/2

與HTTP / 1.1相比,HTTP / 2具備許多優點,可大大下降大規模實時系統的網絡成本。 流提供了用戶將看到的最大靈活性和性能改進之一,可是HTTP / 2還提供了與優美關閉(請參閱:GOAWAY),標頭壓縮,服務器推送,查驗,流優先級等相關的語義。 若是您想了解更多內容,請查看HTTP / 2規範-它很長,可是很容易閱讀。

要當即使用HTTP / 2,請查看gRPC,它是一種使用HTTP / 2的高性能,開源通用RPC框架。 在之後的文章中,咱們將深刻研究gRPC,並探索gRPC如何利用HTTP / 2提供的機制來大規模地提供使人難以置信的高性能通訊。