1. 程式人生 > >HTTP CHUNKED

HTTP CHUNKED

服務端給瀏覽器傳送報文時,必須告訴瀏覽器報文的大小,這樣瀏覽器可以根據報文大小來判斷報文的完整性以及在長連線中確定報文的截尾。但是很多伺服器的報文是動態建立的,在傳送之前是無法確定其大小的。伺服器只有等待內容全部建立後,計算出主體的大小,才能響應客戶端的請求,這樣的處理方法大大延遲了響應。傳輸編碼中的分塊編碼為這種困難提供瞭解決方案,伺服器可以逐塊傳送主體,並說明每塊的大小就可以了。HTTP協議中只定義了兩個首部來描述傳輸編碼:

  • Transfer-Encoding響應首部。告訴瀏覽器傳輸編碼方式,一般為分塊編碼。 
  • TE請求首部。告訴伺服器自己可以接受的編碼方式。

HTTP分塊編碼的響應報文結構大概是這樣的:以HTTP響應首部塊開始

隨後是一系列的分塊。每個分塊包含一個長度值和該分塊的資料,長度值是十六進位制形式並將CRLF與資料分隔開。分塊中資料的大小以位元組計算,不包括長度值和資料之間的CRLF序列。最後是長度為0的結束塊,表示分塊編碼傳輸結束。

假設請求的檔案是jpeg檔案,所以在收到資料之後,只考慮跳過響應報文的HEADER部分加\r\n\r\n四個位元組後,直接把剩餘的資料寫到檔案中。測試過程中,發現有相當一部分圖片不能正常開啟,總是比伺服器多了幾個位元組;列印輸出響應報文後發現頭中並沒有我們通常所見的Content-Length域來指明報文體的長度,反而是多了Transfer – Encoding域。上網查閱http1.1協議後,發現通常情況下,Transfer-Encoding域的值應當為chunked,表明採用chunked編碼方式來進行報文體的傳輸。協議中關於這個欄位的具體解釋如下:

一般HTTP通訊時會使用是Content-Length頭資訊來指定body資訊大小,但是有時候無法確定資訊大小,就要使用trunked編碼動態的提供body內容的長度。進行Chunked編碼傳輸的HTTP資料要在訊息頭部設定:Transfer-Encoding: chunked表示Content Body將用chunked編碼傳輸內容。Chunked編碼一般使用若干個chunk串連而成,最後由一個標明長度為0的chunk標示結束。每個chunk分為頭部和正文兩部分,頭部內容指定下一段正文的字元總數(非零開頭的十六進位制的數字)和數量單位(一般不寫,表示位元組).正文部分就是指定長度的實際內容,

兩部分之間用回車換行(CRLF)隔開。在最後一個長度為0的chunk中的內容是稱為footer的內容,是一些附加的Header資訊(通常可以直接忽略)。

上述解釋過於官方,簡而言之,chunked編碼的基本方法是將大塊資料分解成多塊小資料,每塊都可以自指定長度,其具體格式如下: