通過本文可以了解編寫自己的 HTTP 應(yīng)用程序所需掌握的大部分內(nèi)容。具體來說,你會理解下列概念:
- 報文是如何流動的;
- HTTP 報文的三個組成部分(起始行、首部和實(shí)體的主體部分);
- 請求和響應(yīng)報文之間的區(qū)別;
- 請求報文支持的各種功能(方法);
- 和響應(yīng)報文一起返回的各種狀態(tài)碼;
- 各種各樣的 HTTP 首部都是用來做什么的。
報文流
HTTP 報文是在HTTP 應(yīng)用程序之間發(fā)送的數(shù)據(jù)塊。這些數(shù)據(jù)塊以一些文本形式的元信息(meta-information)開頭,這些信息描述了報文的內(nèi)容及含義,后面跟著可選的數(shù)據(jù)部分。這些報文在客戶端、服務(wù)器和代理之間流動
HTTP 使用術(shù)語流入(inbound)和流出(outbound)來描述事務(wù)處理(transaction)的方向
不管是請求報文還是響應(yīng)報文,所有報文都會向下游(downstream)流動

報文的組成部分
HTTP報文的組成部分:對報文進(jìn)行描述的起始行、包含屬性的頭部塊、可選的,包含數(shù)據(jù)的主體部分

起始行
報文的第一行就是起始行,在請求報文中用來說明要做些什么,在響應(yīng)報文中說明出現(xiàn)了什么情況。
首部字段
起始行后面有零個或多個首部字段。每個首部字段都包含一個名字和一個值,為了便于解析,兩者之間用冒號(:)來分隔。首部以一個空行結(jié)束。添加一個首部字段和添加新行一樣簡單。
主體
空行之后就是可選的報文主體了,其中包含了所有類型的數(shù)據(jù)。請求主體中包括了要發(fā)送給Web 服務(wù)器的數(shù)據(jù);響應(yīng)主體中裝載了要返回給客戶端的數(shù)據(jù)。起始行和首部都是文本形式且都是結(jié)構(gòu)化的,而主體則不同,主體中可以包含任意的二進(jìn)制數(shù)據(jù)(比如圖片、視頻、音軌、軟件程序)。當(dāng)然,主體中也可以包含文本。
報文的語法
所有的HTTP報文都可以分為兩類,請求報文和響應(yīng)報文。請求和響應(yīng)報文的基本報文結(jié)構(gòu)大致是相同的,只有起始行的語法有所不同。
請求報文
它會向Web服務(wù)器請求一個動作請求報文的格式:
起始行: <method> <request-URL> <version>
頭部: <headers>
主體: <entity-body>響應(yīng)報文
它會將請求的結(jié)果返回給客戶端。響應(yīng)報文的格式:
起始行: <version> <status> <reason-phrase>
頭部: <headers>
主體: <entity-body>
下面是對各部分的簡要描述:
1、方式(method):客戶端希望服務(wù)器對資源執(zhí)行的動作,是一個單獨(dú)的詞,比如,GET、POST或HEAD
2、請求URL(request-URL):要直接與服務(wù)器進(jìn)行對話,只要請求URL是資源的絕對路徑就可以了,服務(wù)器可以假定自己是URL的主機(jī)/端口
3、版本(version):報文所使用的HTTP版本。其格式:HTTP/<主要版本號>.<次要版本號>
4、狀態(tài)碼(status-code):狀態(tài)碼是三位數(shù)字,描述了請求過程中所發(fā)生的情況。每個狀態(tài)碼的第一位數(shù)字都用于描述狀態(tài)的一般類別(比如,“成功”、“出錯”等等)
5、原因短語(reason-phrase):數(shù)字狀態(tài)碼的可讀版本,包含行終止序列之前的所有文本。原因短語只對人類有意義,因此,盡管響應(yīng)行HTTP/1.0 200 NOT OK和HTTP/1.0 200 OK中原因短語的含義不同,但同樣都會被當(dāng)作成功指示處理
6、頭部(header):可以有零個或多個頭部,每個首部都包含一個名字,后面跟著一個冒號(:),然后是一個可選的空格,接著是一個值,最后是一個CRLF首部是由一個空行(CRLF)結(jié)束的,表示了頭部列表的結(jié)束和實(shí)體主體部分的開始
7、實(shí)體的主體部分(entity-body):實(shí)體的主體部分包含一個由任意數(shù)據(jù)組成的數(shù)據(jù)塊,并不是所有的報文都包含實(shí)體的主體部分,有時,報文只是以一個CRLF結(jié)束。
展示一些假想的請求和響應(yīng)報文:

起始行
- 請求行
請求報文請求服務(wù)器對資源進(jìn)行一些操作。請求報文的起始行,或稱為請求行,包含了一個方法和一個請求URL,這個方法描述了服務(wù)器應(yīng)該執(zhí)行的操作,請求URL描述了要對哪個資源執(zhí)行這個方法。請求行中還包含HTTP 的版本,用來告知服務(wù)器,客戶端使用的是哪種HTTP。所有這些字段都由空格符分隔 - 響應(yīng)行
響應(yīng)報文承載了狀態(tài)信息和操作產(chǎn)生的所有結(jié)果數(shù)據(jù),將其返回給客戶端。響應(yīng)報文的起始行,或稱為響應(yīng)行,包含了響應(yīng)報文使用的HTTP 版本、數(shù)字狀態(tài)碼,以及描述操作狀態(tài)的文本形式的原因短語。 所有這些字段都由空格符進(jìn)行分隔。
例如:HTTP/1.1 200 OK
首部
- 每個HTTP 首部都有一種簡單的語法:名字后面跟著冒號(:),然后跟上可選的空格,再跟上字段值,最后是一個CRLF。(或者換行符)
常見的首部實(shí)例

- 首部延續(xù)行
將長的首部行分為多行可以提高可讀性,多出來的每行前面至少要有一個空格或制表符(tab)。
HTTP/1.0 200 OK
Content-Type: image/gif
Content-Length: 8572
Server: Test Server
Version 1.0
在這個例子中,響應(yīng)報文里包含了一個 Server 首部,其值被劃分成了多個延續(xù)行。
該首部的完整值為 Test Server Version 1.0。 - 通用首部
這些是客戶端和服務(wù)器都可以使用的通用首部??梢栽诳蛻舳恕⒎?wù)器和其他應(yīng)
用程序之間提供一些非常有用的通用功能。比如,Date 首部就是一個通用首部,
每一端都可以用它來說明構(gòu)建報文的時間和日期:
Date: Tue, 3 Oct 1974 02:16:00 GMT - 請求首部
從名字中就可以看出,請求首部是請求報文特有的。它們?yōu)榉?wù)器提供了一些額
外信息,比如客戶端希望接收什么類型的數(shù)據(jù)。例如,下面的Accept 首部就用
來告知服務(wù)器客戶端會接受與其請求相符的任意媒體類型:
Accept: /
Accept首部

安全請求首部

- 響應(yīng)首部
響應(yīng)報文有自己的首部集,以便為客戶端提供信息(比如,客戶端在與哪種類型
的服務(wù)器進(jìn)行交互)。例如,下列Server 首部就用來告知客戶端它在與一個版
本1.0 的Tiki-Hut 服務(wù)器進(jìn)行交互:
Server: Tiki-Hut/1.0 - 實(shí)體首部
實(shí)體首部指的是用于應(yīng)對實(shí)體主體部分的首部。比如,可以用實(shí)體首部來說明實(shí)
體主體部分的數(shù)據(jù)類型。例如,可以通過下列Content-Type 首部告知應(yīng)用程
序,數(shù)據(jù)是以iso-latin-1 字符集表示的HTML 文檔:
Content-Type: text/html; charset=iso-latin-1
內(nèi)容首部

- 擴(kuò)展首部
擴(kuò)展首部是非標(biāo)準(zhǔn)的首部,由應(yīng)用程序開發(fā)者創(chuàng)建,但還未添加到已批準(zhǔn)的
HTTP 規(guī)范中去。即使不知道這些擴(kuò)展首部的含義,HTTP 程序也要接受它們并
對其進(jìn)行轉(zhuǎn)發(fā)。
方法
常見的http方法

最常接觸的方法是HEAD GET POST。
1.GET
通常用于請求服務(wù)器發(fā)送某個資源。

2.HEAD
HEAD 方法與GET 方法的行為很類似,但服務(wù)器在響應(yīng)中只返回首部。不會返回實(shí)體的主體部分。這就允許客戶端在未獲取實(shí)際資源的情況下,對資源的首部進(jìn)行檢查。
使用HEAD,可以:在不獲取資源的情況下
· 了解資源的情況(比如,判斷其類型);
· 通過查看響應(yīng)中的狀態(tài)碼,看看某個對象是否存在;
· 通過查看首部,測試資源是否被修改了。

3.post
通常用于向服務(wù)器提交數(shù)據(jù)。表單提交常常用到post。

狀態(tài)碼
