HTTP自1990 年以來(lái)就被全球信息網(wǎng)采用為基礎通訊協(xié)議,它是一種應用層的通訊協(xié)議,特性是輕便、快速,特別適合如Web 這種分布式、合作式的超媒體信息系統。HTTP 雖早自1990 年起就已被普遍使用,但過(guò)去許多年并無(wú)統一規范,此項不明確的規范后來(lái)通稱(chēng)為HTTP/0.9。直到1996 年6 月一份僅供參考的文件才由Internet Society 的HTTP Working Group 出版,稱(chēng)為HTTP/1.0。
HTTP/1.0 傳輸格式就像大部分的網(wǎng)絡(luò )通訊協(xié)議,HTTP 使用C/S模式。但是,HTTP/1.0沒(méi)有充分考慮到分層代理,高速緩存的作用以及對穩定連接和虛擬主機的需求。并且隨著(zhù)不完善的進(jìn)程應用的激增,HTTP/1.0迫切需要一個(gè)新的版本,以便使兩個(gè)通信應用程序能夠確定彼此的真實(shí)性能。
這里規定的協(xié)議叫做“HTTP/1.1”,這個(gè)協(xié)議與HTTP/1.0相比,要求更為嚴格,以確保各項功能得到可靠實(shí)現。
在我們日常生活中最常見(jiàn)的應用環(huán)境就是上網(wǎng)瀏覽網(wǎng)頁(yè),很多上班族到辦公室的第一件事就是打開(kāi)電腦,而開(kāi)機后的第一件事就是打開(kāi)IE、Firefox、Myie、GreenBrowser、Opera等瀏覽器時(shí),做的第一件事就是瀏覽一下例如www.sina.com.cn, www.163.com的新聞,而這種簡(jiǎn)單的應用操作,完成的交互過(guò)程就是一個(gè)典型的HTTP協(xié)議的應用過(guò)程。
基于HTTP協(xié)議的客戶(hù)/服務(wù)器模式的信息交換過(guò)程,它分四個(gè)過(guò)程:建立連接、發(fā)送請求信息、發(fā)送響應信息、關(guān)閉連接。如圖1
HTTP_圖1
顯而易見(jiàn)有如下4個(gè)交互的過(guò)程:
連接的建立是通過(guò)申請套接字(Socket)實(shí)現的??蛻?hù)打開(kāi)一個(gè)套接字并把它約束在一個(gè)端口上,如果成功,就相當于建立了一個(gè)虛擬文件。以后就可以在該虛擬文件上寫(xiě)數據并通過(guò)網(wǎng)絡(luò )向外傳送。通俗地說(shuō)就是TCP的三次握手。
首先,這個(gè)消息是用普通的ASCII文本書(shū)寫(xiě)的。這個(gè)消息共有多行(每行以一個(gè)回車(chē)符和一個(gè)換行符結束),最后一行后面還有額外的一個(gè)回車(chē)符和換行符。當然,一個(gè)請求消息也可以?xún)H僅只有一行。請求的報文中包含了各種信息,包括客戶(hù)端想要訪(fǎng)問(wèn)的URL,HTTP的版本,支持的瀏覽的字體等內容。詳細分析見(jiàn)2.2.1請求報文字段。
服務(wù)器在處理完客戶(hù)的請求之后,要向客戶(hù)機發(fā)送響應消息。
這個(gè)響應消息分為3部分:1個(gè)起始的狀態(tài)行(status line),6個(gè)頭部行(不固定)、1個(gè)包含所請求對象本身的附屬體。狀態(tài)行有3個(gè)字段:協(xié)議版本字段、狀態(tài)碼字段、原因短語(yǔ)字段。詳細分析見(jiàn)2.2.2應答報文字段。
客戶(hù)和服務(wù)器雙方都可以通過(guò)關(guān)閉套接字來(lái)結束TCP/IP對話(huà)。通俗地說(shuō)就是TCP的4次握手斷開(kāi)。常見(jiàn)的應用環(huán)境就是這樣,實(shí)際生活中可能就是多了一個(gè)NAT轉換,其實(shí)過(guò)程都是一樣的。
在很多網(wǎng)絡(luò )安全產(chǎn)品中,提供了HTTP過(guò)濾的功能,要求客戶(hù)在IE瀏覽器上做一個(gè)【Internet選項】->【連接】->【局域網(wǎng)設置】的更改,配置代理的ip和端口。如下圖2:
HTTP_圖2
點(diǎn)擊【局域網(wǎng)設置】后輸入ip和端口,并鉤選“為L(cháng)AN使用代理服務(wù)器”如下圖3:
HTTP_圖3
客戶(hù)端和代理主機間用交換機相連,下面的拓撲中為了看得更加清晰并沒(méi)有畫(huà)出交換機。
下面是一個(gè)簡(jiǎn)單的拓撲圖4:
HTTP_圖4
詳細的交互過(guò)程分析參見(jiàn):3.3
HTTP報文格式并不復雜,但是各個(gè)字段類(lèi)型數量龐大,這里只對常見(jiàn)的字段進(jìn)行分析。
對于下面字段說(shuō)明中出現的一些常見(jiàn)字符作一下說(shuō)明:
“文字”
文字原文使用引號。除特殊情況,原文對外界不敏感。
規則1 | 規則2
由豎線(xiàn)("|")分開(kāi)的元素是可選的,例如,"yes | no"表示yes或no都是可接受的。
(規則1 規則2)
圍在括號里的多個(gè)元素視作一個(gè)元素。這樣“(elem (foo | bar) elem)”允許標記序列“elem foo elem”和elem bar elem”。
*規則
前面的字符"*"表示重復。完整的形式是"*元素",表示元素至少出現次,至多出現次。默認值是0和無(wú)窮大,所以"*(元素)"允許任何數值,包括零;"1*元素"至少需要一次;"1*2element"允許一次或兩次。
[規則]
方括號里是任選元素;"[foo bar]"相當于"*1(foo bar)"。
對于HTTP的報文格式分析,就是兩種格式,因為基于C/S的訪(fǎng)問(wèn)應答模式,所以一個(gè)是請求的報文格式,而另一個(gè)是應答的報文格式。
先看一下請求報文格式的作圖,如圖5:
HTTP_圖5
文本分析一下請求報文的內容:
請求 =請求行 Request Line
*((常規報頭 General Header
|請求報頭 Request Header
|實(shí)體報頭)CRLF) Entity Header
CRLF
[消息正文] Message Body
說(shuō)明:
HTTP/1.1將CR LF的順序定義為任何協(xié)議元素的行尾標志,CR= LF= 。
先看一下應答報文格式的作圖,如圖6:
HTTP_圖6
文本分析一下應答報文的內容:
應答 ?。綘顟B(tài)行 Status Line
*((常規報頭(general-header) General Header
|應答報頭(response-header) Response Header
|實(shí)體報頭(entity-header)CRLF) Entity Header
CRLF
[應答正文] Message Body
根據上面提到的請求報文和應答報文的格式,對每個(gè)字段進(jìn)行描述。
如圖7:
HTTP_圖7
請求消息的第一行稱(chēng)為請求行(request line),請求行有3個(gè)字段:
方法字段(Request Method)圖7中為:GET;
URL字段(Request URL)圖7中為:/forumdisplay.php?fid=6,這個(gè)字段可以是一個(gè)“/;
HTTP協(xié)議不對URL的長(cháng)度作事先的限制.服務(wù)器必須能夠處理它們服務(wù)的任何資源的URL,并且應該能夠處理無(wú)限長(cháng)度的URL,如果它們提供可以產(chǎn)生這種URL的基于GET的形式。
HTTP版本字段(Request Version)。圖7中為:HTTP/1.1。
看一下RFC2616中的截圖8:
HTTP_圖8
常見(jiàn)的方法字段說(shuō)明:
GET: 請求指定的頁(yè)面信息,并返回實(shí)體主體。
HEAD: 只請求頁(yè)面的首部。
POST:請求服務(wù)器接受所指定的文檔作為對所標識的URL的新的從屬實(shí)體。
PUT: 從客戶(hù)端向服務(wù)器傳送的數據取代指定的文檔的內容。
DELETE: 請求服務(wù)器刪除指定的頁(yè)面。
OPTIONS: 允許客戶(hù)端查看服務(wù)器的性能。
需要特別說(shuō)明的是方法字段有若干個(gè)值可供選擇,最常見(jiàn)的包括GET、POST和HEAD。
而且HEAD字段并不好抓包顯示,但是這個(gè)字段的作用卻需要注意,HTML中的head標記是網(wǎng)頁(yè)標記中一個(gè)非常重要的符號,head標記中包含的內容基本上描述了所屬頁(yè)面的基本屬性,包括標題、字符集、站點(diǎn)信息、網(wǎng)站作者信息、站點(diǎn)描述、站點(diǎn)關(guān)鍵詞、搜索引擎蜘蛛引導、刷新及跳轉、樣式表鏈入以及其它一些有用的附加功能。例如:
簡(jiǎn)體中文:“ ”
繁體中文:“ ”
英 語(yǔ):“”
禁止瀏覽器從本地機的緩存中調閱頁(yè)面內容。
例子:“ ”
/P>
后續各行都稱(chēng)為請求頭部行(header),即請求報頭。其中RFC2616中定義常見(jiàn)的有:
HTTP_圖9
常見(jiàn)的頭部說(shuō)明:
Accept:可以接受的媒體;
Accept-Charset:可以接受的字符集;
Accept-Encoding:可以接受的編碼方案;
Accept-Language:能夠接受的語(yǔ)言;
Host:主機和端口號;
Referer:指明被連接的目標URL。
同時(shí)RFC2616注明可以根據需要擴展自定義的頭部行:
原文:Request-header field names can be extended reliably only in combination with a change in the protocol version. However, new or experimental header fields MAY be given the semantics of request-header fields if all parties in the communication recognize them to be request-header fields. Unrecognized header fields are treated as entity-header fields.
翻譯:隨著(zhù)協(xié)議版本的變化,請求報頭域的名字可以可靠的擴展。然而新的或擴展的報頭域可以給出請求報頭域的語(yǔ)法,其前提是通信中所有部分承認它們是請求報頭域。不被承認的報頭域被當作實(shí)體報頭域。
如圖10:
HTTP_圖10
應答信息的第一行是狀態(tài)行,由協(xié)議版本以及數字狀態(tài)碼和相關(guān)的文本說(shuō)明組成,各部分間用空格符隔開(kāi),除了最后的回車(chē)或換行外,中間不允許有回車(chē)換行,注意HTTP/1.1后面沒(méi)有rn。
狀態(tài)行中的狀態(tài)碼是試圖理解和滿(mǎn)足請求的三位數字的整數碼,狀態(tài)碼用于自動(dòng)控制而注解短語(yǔ)是面向用戶(hù)的,客戶(hù)機不需要檢查和顯示注解短語(yǔ)。
圖10中返回的協(xié)議版本為HTTP/1.1,注意,請求的HTTP版本可以和返回的HTTP不一致。返回的狀態(tài)碼為200 OK。
狀態(tài)碼的第一位數字定義應答類(lèi)型,后兩位數字沒(méi)有任何類(lèi)型任務(wù),第一位數字有五種值:
-1xx: 報告的 - 接收到請求,繼續進(jìn)程.
-2xx 成功 - 操作成功的收到.
-3xx 重發(fā) - 為了完成請求,必須采取進(jìn)一步措施.
-4xx 客戶(hù)端出錯 - 請求包括錯的順序或不能完成.
-5xx 服務(wù)器出錯 - 服務(wù)器無(wú)法完成顯然有效的請求.
HTTP協(xié)議狀態(tài)碼的具體含義 :
"100" : Continue 繼續;
"101" : witching Protocols 轉換協(xié)議;
"200" : OK 成功;
"201" : Created 創(chuàng )建;
"202" : Accepted 接受;
"203" : Non-Authoritative Information 非權威信息;
"204" : No Content 無(wú)內容;
"205" : Reset Content 重置內容;
"206" : Partial Content 局部?jì)热荩?/p>
"300" : Multiple Choices 多樣選擇;
"301" : Moved Permanently 永久移動(dòng);
"302" : Found 創(chuàng )立;
"303" : See Other 觀(guān)察別的部分;
"304" : Not Modified 只讀;
"305" : Use Proxy 用戶(hù)代理;
"307" : Temporary Redirect 臨時(shí)重發(fā);
"400" : Bad Request 壞請求;
"401" : Unauthorized 未授權的;
"402" : Payment Required 必要的支付;
"403" : Forbidden 禁用;
"404" : Not Found 沒(méi)找到;
"405" : Method Not Allowed 不允許的方式;
"406" : Not Acceptable 不接受;
"407" : Proxy Authentication Required 需要代理驗證;
"408" : Request Time-out 請求超時(shí);
"409" : Conflict 沖突;
"410" : Gone 以往的;
"411" : Length Required 需要的長(cháng)度;
"412" : Precondition Failed 預處理失??;
"413" : Request Entity Too Large 請求實(shí)體太大;
"414" : Request-URL Too Large 請求URL太大;
"415" : Unsupported Media Type 不支持的媒體類(lèi)型;
"416" : Requested range not satisfiable 請求的范圍不足;
"417" : Expectation Failed 期望失??;
"500" : Internal Server Error 服務(wù)器內部出錯;
"501" : Not Implemented 不能實(shí)現;
"502" : Bad Gateway 壞網(wǎng)關(guān);
"503" : Service Unavailable 服務(wù)器不能實(shí)現;
"504" : Gateway Time-out 網(wǎng)關(guān)超時(shí);
"505" : HTTP Version not supported HTTP版本不支持。
應答頭允許服務(wù)器傳送應答的附加信息,這些信息不能放在狀態(tài)行里.這些報頭域給出有關(guān)服務(wù)器的信息以及請求URL指定的資源的下一步的通路。
RFC2616中定義的應答頭部行,圖11:
HTTP_圖11
常見(jiàn)的應答頭部說(shuō)明:
Accept-Ranges:給出客戶(hù)請求的范圍;
Age:給出文檔的使用期限;
Location:重新定向后的位置;
Server:給出服務(wù)器和版本號。
隨著(zhù)協(xié)議版本的變化,應答報頭可以可靠的擴展。而且,如果通信的所有組成部分都把它當作應答報頭域,新的或試驗性的應答報頭域可以被給定應答報頭域的含義,未被承認的報頭域被當作實(shí)體報頭域。
這個(gè)字段可能經(jīng)常被誤以為是頭部字段中的內容,在未經(jīng)特別規定的情況下,請求與應答的報文也可以傳送實(shí)體。實(shí)體包括實(shí)體報頭與實(shí)體正文,而有些應答只包括實(shí)體報頭。
實(shí)體報文域定義了關(guān)于實(shí)體正文的維護信息(參數),或在無(wú)正文情況下定義了請求的資源。其中一些參數是可選的,一些則是由技術(shù)指標規定必須的。
參見(jiàn)RFC2612的圖12:
HTTP_圖12
可以從中看出實(shí)體字段主要規定的是內容編碼(Content-Encoding)、內容類(lèi)型(Content-Type)、內容語(yǔ)言(Content-Language)、內容長(cháng)度(Content-Length)、上次修改(Last-Modified)等信息。
經(jīng)由HTTP請求或應答發(fā)送的實(shí)體正文部分(如果存在的話(huà))的格式與編碼方式應由實(shí)體報文域決定。
實(shí)體正文= *八位字節
實(shí)體正文只有當報文正文存在時(shí)才存在。實(shí)體正文是通過(guò)對報文正文按某種保證安全性且便于傳輸的傳輸編碼進(jìn)行解碼得到的。對于報文中的實(shí)體正文而言,其數據類(lèi)型由報頭中的"內容類(lèi)型"與"內容編碼"域決定。也即定義了一個(gè)雙層有序的編碼模型:
實(shí)體正文=內容編碼(內容類(lèi)型(數據))
"內容類(lèi)型"規定了基本數據的媒體類(lèi)型。
"內容編碼"則可用來(lái)指明對數據施加的任何附加的,通常以數據壓縮為目的的編碼方式,并將其作為所請求資源的一項屬性。沒(méi)有缺省的編碼方式。
任一包含了實(shí)體正文的HTTP/1.1報文都應包括"內容類(lèi)型"(Content-Type)報頭域,以定義正文的媒體類(lèi)型。當且僅當"內容類(lèi)型"域未給出媒體類(lèi)型時(shí),接收者才可以通過(guò)查看資源的內容,擴展名或URL來(lái)猜測其媒體類(lèi)型。若媒體類(lèi)型仍然未知,接收者應將其作為"應用/八位字節流"來(lái)處理。
報文的實(shí)體長(cháng)度指的是在對報文進(jìn)行傳輸編碼前報文正文的長(cháng)度。圖10中標記的內容長(cháng)度。
在持續連接之前,為獲取每一URL都建立了獨立的TCP 連接,這就加重了HTTP服務(wù)器的負擔,易引起INTERNET阻塞。嵌入式圖片與其它相關(guān)數據通常使用戶(hù)在短時(shí)間內對同一服務(wù)器提交多個(gè)請求。HTTP/1.1 與HTTP/1.0 版本的一個(gè)顯著(zhù)區別在于持續連接是任何HTTP連接的缺省方式。也就是說(shuō),除非另有指定,客戶(hù)機總應當假定服務(wù)器會(huì )保持持續連接,即便在接到服務(wù)器的出錯應答時(shí)也應如此。
注意:在測試驗證過(guò)程中出現過(guò)一種特殊情況,在IE上設置代理上網(wǎng),在代理服務(wù)器上(如圖4)抓到的報文卻是HTTP/1.0的請求。改用Firefox瀏覽器設置代理上網(wǎng)卻不會(huì )出現這個(gè)情況。后來(lái)發(fā)現是IE自身設置的問(wèn)題,在【internet選項】->【高級】->HTTP1.1設置中有一個(gè)【通過(guò)代理連接使用HTTP1.1】的鉤選項。
持續HTTP 連接有著(zhù)諸多的優(yōu)點(diǎn):
--- 通過(guò)建立與關(guān)閉較少的連接,不僅節省了路由器與主機(客戶(hù)機,服務(wù)器,代理服務(wù)器,網(wǎng)關(guān),隧道或高速緩沖存儲機)的CPU時(shí)間,還節省了主機用于TCP協(xié)議控制塊的內存。
--- HTTP請求與應答可以進(jìn)入連接流水線(xiàn)。流水線(xiàn)方式使得客戶(hù)無(wú)須挨個(gè)等待應答即發(fā)起多個(gè)請求,從而更充分的利用了單個(gè)的TCP連接,減少了崩潰時(shí)間。
--- 在減少TCP連接中數據包個(gè)數的同時(shí),使TCP有了充裕的時(shí)間來(lái)確定網(wǎng)絡(luò )的擁塞狀況,緩解了網(wǎng)絡(luò )擁塞。
--- 因為無(wú)須在創(chuàng )建TCP連接握手上耗費時(shí)間,而使連續請求造成的延遲現象得到改善。
--- 由于出錯不會(huì )導致TCP連接的關(guān)閉,HTTP可以更好的實(shí)現自我完善。使用較新版HTTP的用戶(hù)會(huì )樂(lè )于嘗試一些新功能,與舊版服務(wù)器通信時(shí),則會(huì )在接到出錯報告后用舊模式重試。
聯(lián)系客服