閱讀663 返回首頁    go 小米 go 小米手環


讀RFC 2616(超文本傳輸協議——HTTP1.1)筆記

在 HTTP/1.0 中,大多實現為每個請求/響應交換使用新的連接。在 HTTP/1.1 中,一個連接可用於一次或多次請求/響應交換,盡管連接可能由於各種原因被關閉.這是他們之間最大的分別.

有關URI的長度.服務器應當小心決定 URI 長度超過 255 字節,因為一些老的客戶端或代理實現可能不能正確支持這種長度。

HTTP 日期/時間戳【必須】以格林尼製標準時間(GMT)表示.所以我們中國的時區有8個小時的分別.

為了與 HTTP/1.0 應用程序兼容,包含 message-body 的 HTTP/1.1 請求【必須】包括有效的 Content-Length 頭部域,除非已知服務器與 HTTP/1.1 兼容。如果請求包含 message-body但沒有給出 Content-Length,則服務器【應該】在不能判斷消息長度時用 400(Bad Request)響應,或在希望堅持接收有效 Content-Length 時用 411(Length Required)響應

在http中的Request的結構.

Request = Request-Line ; 5.1 節

*(( general-header ; 4.5 節

| request-header ; 5.3 節

| entity-header ) CRLF) ; 7.1 節

總結:Request(  在消息的首先中,從客戶端到服務器的請求消息包括應用到資源的方法、資源的標識符和使用的協議版本。相當我們對網站的http的請求)

Request-Line = Method SP Request-URI SP HTTP-Version CRLF

Method = “OPTIONS” ; 9.2 節

| “GET” ; 9.3 節

| “HEAD” ; 9.4 節

| “POST” ; 9.5 節

| “PUT” ; 9.6 節

| “DELETE” ; 9.7 節

| “TRACE” ; 9.8 節

| “CONNECT” ; 9.9 節

| extension-method

extension-method = token

Request-URI = “*” | absoluteURI | abs_path | authority

request-header = Accept ; 14.1 節

| Accept-Charset ; 14.2 節

| Accept-Encoding ; 14.3 節

| Accept-Language ; 14.4 節

| Authorization ; 14.8 節

| Expect ; 14.20 節

| From ; 14.22 節

| Host ; 14.23 節

| If-Match ; 14.24 節

| If-Modified-Since ; 14.25 節

| If-None-Match ; 14.26 節

| If-Range ; 14.27 節

| If-Unmodified-Since ; 14.28 節

| Max-Forwards ; 14.31 節

| Proxy-Authorization ; 14.34 節

| Range ; 14.35 節

| Referer ; 14.36 節

| TE ; 14.39 節

| User-Agent ; 14.43 節

Response = Status-Line ; 6.1 節

*(( general-header ; 4.5 節

| response-header ; 6.2 節

| entity-header ) CRLF) ; 7.1 節

CRLF

[ message-body ] ; 7.2 節

總結:Response(在接收並解析請求消息後,服務器以 HTTP 響應消息響應。相當服務器對客戶的http的回應)

Status-Line = HTTP-Version SP Status-Code SP Reason-Phrase CRLF

Status-Code 的首位數字定義響應的類別。最後兩個數字沒有任何分類。首位數字有 5個值:

·1xx:   信息性——收到請求,繼續處理

·2xx:   成功性——成功收到、理解並接受行動

·3xx:   重定向——必須采取進一步行動來完成請求

·4xx:   客戶端錯誤——請求包含錯誤語法或不能完成

·5xx:   服務器錯誤——服務器沒有成功完成顯然有效的請求

(這個是我們常常講的http的狀態碼)Status-Code = “100″ ; 10.1.1 節: Continue

| “101″ ; 服務器理解並願意答應客戶端的請求: Switching Protocols

| “200″ ; 請求已經成功: OK

| “201″ ; 請求全部成功,且創建了新資源: Created

| “202″ ; 請求已經接受處理,但是處理還沒有完成: Accepted

| “203″ ; 10.2.4 節: Non-Authoritative Information

| “204″ ; 10.2.5 節: No Content

| “205″ ; 10.2.6 節: Reset Content

| “206″ ; 10.2.7 節: Partial Content

| “300″ ; 10.3.1 節: Multiple Choices

| “301″ ; 所請求的資源已經指定到一個新的永久 URI: Moved Permanently

| “302″ ; 所請求的資源臨時存在於不同的 URI: Found

| “303″ ; 10.3.4 節: See Other

| “304″ ; 但文檔沒有變化: Not Modified

| “305″ ; 10.3.6 節: Use Proxy

| “307″ ; 10.3.8 節: Temporary Redirect

| “400″ ; 服務器不能理解請求,由於畸形的語法: Bad Request

| “401″ ; 10.4.2 節: Unauthorized

| “402″ ; 10.4.3 節: Payment Required

| “403″ ; 10.4.4 節: Forbidden

| “404″ ; 服務器不能發現匹配 Request-URI 的任何東西: Not Found

| “405″ ; 10.4.6 節: Method Not Allowed

| “406″ ; 10.4.7 節: Not Acceptable

| “407″ ; 10.4.8 節: Proxy Authentication Required

| “408″ ; 10.4.9 節: Request Time-out

| “409″ ; 10.4.10 節: Conflict

| “410″ ; 10.4.11 節: Gone

| “411″ ; 10.4.12 節: Length Required

| “412″ ; 10.4.13 節: Precondition Failed

| “413″ ; 10.4.14 節: Request Entity Too Large

| “414″ ; 10.4.15 節: Request-URI Too Large

| “415″ ; 10.4.16 節: Unsupported Media Type

| “416″ ; 10.4.17 節: Requested range not satisfiable

| “417″ ; 10.4.18 節: Expectation Failed

| “500″ ; 10.5.1 節: Internal Server Error

| “501″ ; 10.5.2 節: Not Implemented

| “502″ ; 當作為網關或代理時,服務器從它靠近的上遊服務器收到試圖完成請求的無效響應: Bad Gateway

| “503″ ; 服務器當前不能處理請求,因為臨時性的負載過重或服務器維護中。: Service Unavailable

| “504″ ; 10.5.5 節: Gateway Time-out

| “505″ ; 10.5.6 節: HTTP Version not supported

| extension-code

extension-code = 3DIGIT

Reason-Phrase = *<TEXT,除 CR, LF 外>

response-header = Accept-Ranges ; 14.5 節

| Age ; 14.6 節

| ETag ; 14.19 節

| Location ; 14.30 節

| Proxy-Authenticate ; 14.33 節

| Retry-After ; 14.37 節

| Server ; 14.38 節

| Vary ; 14.44 節

| WWW-Authenticate ; 14.47 節

entity-header = Allow ; 14.7 節

| Content-Encoding ; 14.11 節

| Content-Language ; 14.12 節

| Content-Length ; 14.13 節

| Content-Location ; 14.14 節

| Content-MD5 ; 14.15 節

| Content-Range ; 14.16 節

| Content-Type ; 14.17 節

| Expires ; 14.21 節

| Last-Modified ; 14.29 節

| extension-header

extension-header = message-header

HTTP/1.1 與較早版本的 HTTP 的明顯區別是永久連接是任何 HTTP 連接的缺省行為。  該信號使用 Connection 頭部域(14.10 節)來發生。一旦收到關閉信號,客戶端<禁止>再發送任何更多的請求在該連接上。    HTTP/1.1 服務器<可以>假設 HTTP/1.1 客戶端打算維護永久連接,除非所發送請求中的

Connection 頭部中包括連接記號“close”。如果服務器選擇在發送響應後立即關閉連接,它<應該>發送包括關閉連接記號的 Connection 頭部。

總結:有關鏈接數.所以可以講,在一個網頁中,在http頭中的Connection中有多少個close的頭,就相當有多少個http的連接.

服務器既可使用 Expires 頭部,也可使用 Cache-Control 頭部的 max-age(最大年齡值)指令來指定明確的截止時間。截止時間不能使用強製用戶代理刷新它的顯示或重新加載資源;它的語義隻應用到緩存機製.

max-age 指令優先於 Expires,所以如果響應中存在 max-age,則計算是簡單的:

更新周期=最大年齡值

否則,如果 Expires 存在於響應中,則計算方法是:

更新周期=截止值-日期值

總結:說明有Expires頭和Cache-Control頭後.緩存服務器是會根據這個來斷定是否更新.這二個值優先級最高.

既然原始服務器並非始終提供明確的截止時間,HTTP 緩存服務器一般指它啟發式截止時間,用使用其它頭部值(如同 Last-Modified 時間)的算法來估計好象有理的截止時間。

總結:squid之類,如果沒有指明前二個的截止時間,那它就會使用發式截止時間,如參考 Last-Modified.

HTTP/1.1 需要原始服務器盡可能在每個響應中發送 Date 頭部,它給響應生成的時間.

HTTP/1.1 使用 Age 響應頭部來傳輸從緩存服務器獲取時的響應消息的估計年齡。Age域值是緩存服務器估計從響應產生或被原始服務器重新證實以來的總時間

, Age 值是響應已經在從原始服務器到每個緩存服務器中停留的總時間,加上在網絡路徑上傳輸的總時間。

年齡值”表示 Age 頭部的值,以適合算法運算的形式。

響應的年齡可以用兩種完全獨立的方式來計算:

1、“現在”減去“日期值” ,如果假設本地時鍾與原始服務器的時鍾很好地同步。如果結果是負數,則結果用 0 代替。

2、“年齡值”,如果響應路徑上的所有緩存服務器都實現 HTTP/1.1。

上麵給出我們有兩種獨立的方式計算所收到響應的年齡,   我們可以將它們組合為: 正確的接收年齡=取最大值(現在-日期值,年齡值) 且如果我們有幾乎同步的時鍾或全為 HTTP/1.1的路徑,就可得到可靠(保守的)的結果。

總結當緩存服務器收到響應的年齡的計算算法:

/*

* 年齡值

*    是 Age 的值:緩存服務器收到的該響應的頭部

* 日期值

*    是原始服務器 Date 頭部的值

* 請求時間

*    是緩存服務器作出導致緩存服務器的響應的請求的(本地)時間

* 響應時間

*    緩存服務器收到響應的(本地)時間

* 現在

*    當前(本地)時間

*/

外觀年齡=取最大值(0,響應時間-日期值)   ;

修正接收年齡=取最大值(外觀年齡,年齡值)     ;

響應延遲=響應時間-請求時間;

修正發起年齡=修正接收年齡+響應延遲;

常駐時間=現在-響應時間;

當前年齡=修正發起年齡+常駐時間;

響應中存在 Age 頭部意味著該響應不是第一手的。然而,返過來就不成立,因為響應中缺少 Age 頭部域並不意味著該響應是第一手的,除非請求路徑上的所有緩存服務器都與HTTP/1.1 一致(例如,老版 HTTP 緩存服務器並不實現 Age 頭部域)

總結:其實這個我很多不明白…下次在看看,有一點明白,如果中間有緩存服務器,就會有個age的頭,age的值是緩存服務器算出來的,原始服務器是沒有的.

public  指出該響應【可以】被任何緩存器緩存,即使它通常是不可緩存的(其它細節另見 Authorization、14.8或隻在非共享緩存中可緩存的。)

private 指出響應消息中的所有部分是用於單個用戶的且【禁止】被共享緩存器所緩存。這允許原始服務器使隻用於一個用戶的響應和對其他用戶所請求的無效響應的指定部分過期。私有(非共享)緩存【可以】緩存該響應。

總結:這二個很有意思。基實理解為public可以在任何地方被緩存就好了,如中間的緩存服務器和客戶端的IE.但private在中間的緩存服務器是不能緩存的,隻有用戶的IE可以.

最後更新:2017-01-04 22:34:34

  上一篇:go 做了CDN獲取用戶真實IP的方法 PHP與Asp設置方式
  下一篇:go bind+dlz+mysql