上一篇介紹了HTTP協(xié)議的版本迭代歷史,本篇繼續(xù)深入介紹一下HTTP協(xié)議的規(guī)范,本文主要介紹它的URI、Request、Response、狀態(tài)碼等等信息,通過(guò)了解這些具體的內(nèi)容,可以更直觀的理解HTTP的協(xié)議格式,以及工作原理。
一、URI結(jié)構(gòu)
HTTP使用統(tǒng)一資源標(biāo)識(shí)符(URI)來(lái)傳輸數(shù)據(jù)和建立連接。URL(統(tǒng)一資源定位符)是一種特殊種類的URI,包含了用于查找的資源的足夠的信息,我們一般常用的就是URL,而一個(gè)完整的URL包含下面幾部分:
http://www.fishbay.cn:80/mix/76.html?name=kelvin&password=123456#first
1.協(xié)議部分
該URL的協(xié)議部分為http:,表示網(wǎng)頁(yè)用的是HTTP協(xié)議,后面的//為分隔符
2.域名部分
域名是www.fishbay.cn,發(fā)送請(qǐng)求時(shí),需要向DNS服務(wù)器解析IP。如果為了優(yōu)化請(qǐng)求,可以直接用IP作為域名部分使用
3.端口部分
域名后面的80表示端口,和域名之間用:分隔,端口不是一個(gè)URL的必須的部分。如果端口是80,也可以省略不寫
4.虛擬目錄部分
從域名的第一個(gè)/開始到最后一個(gè)/為止,是虛擬目錄的部分。其中,虛擬目錄也不是URL必須的部分,本例中的虛擬目錄是/mix/
5.文件名部分
從域名最后一個(gè)/開始到?為止,是文件名部分;如果沒有?,則是從域名最后一個(gè)/開始到#為止,是文件名部分;如果沒有?和#,那么就從域名的最后一個(gè)/從開始到結(jié)束,都是文件名部分。本例中的文件名是76.html,文件名也不是一個(gè)URL的必須部分,如果沒有文件名,則使用默認(rèn)文件名
6.錨部分
從#開始到最后,都是錨部分。本部分的錨部分是first,錨也不是一個(gè)URL必須的部分
7.參數(shù)部分
從?開始到#為止之間的部分是參數(shù)部分,又稱為搜索部分、查詢部分。本例中的參數(shù)是name=kelvin&password=123456,如果有多個(gè)參數(shù),各個(gè)參數(shù)之間用&作為分隔符。
二、Request
HTTP的請(qǐng)求包括:請(qǐng)求行(request line)、請(qǐng)求頭部(header)、空行 和 請(qǐng)求數(shù)據(jù) 四個(gè)部分組成。

抓包的request結(jié)構(gòu)如下:
GET /mix/76.html?name=kelvin&password=123456 HTTP/1.1
Host: www.fishbay.cn
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/56.0.2924.87 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Encoding: gzip, deflate, sdch
Accept-Language: zh-CN,zh;q=0.8,en;q=0.6
1.請(qǐng)求行
GET為請(qǐng)求類型,/mix/76.html?name=kelvin&password=123456為要訪問(wèn)的資源,HTTP/1.1是協(xié)議版本
2.請(qǐng)求頭部
從第二行起為請(qǐng)求頭部,Host指出請(qǐng)求的目的地(主機(jī)域名);User-Agent是客戶端的信息,它是檢測(cè)瀏覽器類型的重要信息,由瀏覽器定義,并且在每個(gè)請(qǐng)求中自動(dòng)發(fā)送。
3.空行
請(qǐng)求頭后面必須有一個(gè)空行
4.請(qǐng)求數(shù)據(jù)
請(qǐng)求的數(shù)據(jù)也叫請(qǐng)求體,可以添加任意的其它數(shù)據(jù)。這個(gè)例子的請(qǐng)求體為空。
Response
一般情況下,服務(wù)器收到客戶端的請(qǐng)求后,就會(huì)有一個(gè)HTTP的響應(yīng)消息,HTTP響應(yīng)也由4部分組成,分別是:狀態(tài)行、響應(yīng)頭、空行 和 響應(yīng)體。

抓包的數(shù)據(jù)如下:
HTTP/1.1 200 OK
Server: nginx
Date: Mon, 20 Feb 2017 09:13:59 GMT
Content-Type: text/plain;charset=UTF-8
Vary: Accept-Encoding
Cache-Control: no-store
Pragrma: no-cache
Expires: Thu, 01 Jan 1970 00:00:00 GMT
Cache-Control: no-cache
Content-Encoding: gzip
Transfer-Encoding: chunked
Proxy-Connection: Keep-alive
{"code":200,"notice":0,"follow":0,"forward":0,"msg":0,"comment":0,"pushMsg":null,"friend":{"snsCount":0,"count":0,"celebrityCount":0},"lastPrivateMsg":null,"event":0,"newProgramCount":0,"createDJRadioCount":0,"newTheme":true}
1.狀態(tài)行
狀態(tài)行由協(xié)議版本號(hào)、狀態(tài)碼、狀態(tài)消息組成
2.響應(yīng)頭
響應(yīng)頭是客戶端可以使用的一些信息,如:Date(生成響應(yīng)的日期)、Content-Type(MIME類型及編碼格式)、Connection(默認(rèn)是長(zhǎng)連接)等等
3.空行
響應(yīng)頭和響應(yīng)體之間必須有一個(gè)空行
4.響應(yīng)體
響應(yīng)正文,本例中是鍵值對(duì)信息
三、狀態(tài)碼
HTTP協(xié)議的狀態(tài)碼由3位數(shù)字組成,第一個(gè)數(shù)字定義了響應(yīng)的類別,共有5中類別:
1.1xx: 指示信息--表示請(qǐng)求已接收,繼續(xù)處理
2.2xx: 成功--表示請(qǐng)求已被成功接收、理解、接受
3.3xx: 重定向--要完成請(qǐng)求必須進(jìn)行更進(jìn)一步的操作
4.4xx: 客戶端錯(cuò)誤--請(qǐng)求有語(yǔ)法錯(cuò)誤或請(qǐng)求無(wú)法實(shí)現(xiàn)
5.5xx: 服務(wù)器端錯(cuò)誤--服務(wù)器未能實(shí)現(xiàn)合法的請(qǐng)求
其中,常用的狀態(tài)碼如下:
200 OK //客戶端請(qǐng)求成功
400 Bad Request //客戶端請(qǐng)求有語(yǔ)法錯(cuò)誤,不能被服務(wù)器所理解
401 Unauthorized //請(qǐng)求未經(jīng)授權(quán),這個(gè)狀態(tài)代碼必須和WWW-Authenticate報(bào)頭域一起使用
403 Forbidden //服務(wù)器收到請(qǐng)求,但是拒絕提供服務(wù)
404 Not Found //請(qǐng)求資源不存在,eg:輸入了錯(cuò)誤的URL
500 Internal Server Error //服務(wù)器發(fā)生不可預(yù)期的錯(cuò)誤
503 Server Unavailable //服務(wù)器當(dāng)前不能處理客戶端的請(qǐng)求,一段時(shí)間后可能恢復(fù)正常
如需了解更多的狀態(tài)碼,請(qǐng)參考這個(gè)網(wǎng)址:HTTP狀態(tài)碼
四、請(qǐng)求方法
HTTP定義了多種請(qǐng)求方法,來(lái)滿足各種需求。HTTP/1.0定義了三種請(qǐng)求方法:GET、POST 和 HEAD,到了HTTP/1.1,新增了五種請(qǐng)求方法:OPTIONS、PUT、DELETE、TRACE 和 CONNECT。各個(gè)請(qǐng)求方法的具體功能如下:
GET 請(qǐng)求指定的頁(yè)面信息,并返回實(shí)體主體。
HEAD 類似于get請(qǐng)求,只不過(guò)返回的響應(yīng)中沒有具體的內(nèi)容,用于獲取報(bào)頭
POST 向指定資源提交數(shù)據(jù)進(jìn)行處理請(qǐng)求(例如提交表單或者上傳文件)。數(shù)據(jù)被包含在請(qǐng)求體中。POST請(qǐng)求可能會(huì)導(dǎo)致新的資源的建立和/或已有資源的修改。
PUT 從客戶端向服務(wù)器傳送的數(shù)據(jù)取代指定的文檔的內(nèi)容。
DELETE 請(qǐng)求服務(wù)器刪除指定的頁(yè)面。
CONNECT HTTP/1.1協(xié)議中預(yù)留給能夠?qū)⑦B接改為管道方式的代理服務(wù)器。
OPTIONS 允許客戶端查看服務(wù)器的性能。
TRACE 回顯服務(wù)器收到的請(qǐng)求,主要用于測(cè)試或診斷。
實(shí)際應(yīng)用過(guò)程中,GET和POST使用的比較多,下面主要介紹一下二者的區(qū)別:
1.請(qǐng)求參數(shù)的區(qū)別
GET請(qǐng)求會(huì)把請(qǐng)求的參數(shù)拼接在URL后面,以?分隔,多個(gè)參數(shù)之間用&連接;如果是英文或數(shù)字,原樣發(fā)送,如果是空格或中文,則用Base64編碼
POST請(qǐng)求會(huì)把提交的數(shù)據(jù)放在請(qǐng)求體中,不會(huì)在URL中顯示出來(lái)
2.傳輸數(shù)據(jù)的大小
GET: 瀏覽器和服務(wù)器會(huì)限制URL的長(zhǎng)度,所以傳輸?shù)臄?shù)據(jù)有限,一般是2K
POST: 由于數(shù)據(jù)不是通過(guò)URL傳遞,所以一般可以傳輸較大量的數(shù)據(jù)
3.數(shù)據(jù)解析
GET: 通過(guò)Request.QueryString獲取變量的值
POST: 通過(guò)Request.form獲取變量的值
4.安全性
GET: 請(qǐng)求參數(shù)在URL后面,可以直接看到,尤其是登錄時(shí),如果登錄界面被瀏覽器緩存,其他人就可以通過(guò)查看歷史記錄,拿到賬戶和密碼
POST: 請(qǐng)求參數(shù)在請(qǐng)求體里面?zhèn)鬏敚瑹o(wú)法直接拿到,相對(duì)GET安全性較高;但是通過(guò)抓包工具,還是可以看到請(qǐng)求參數(shù)的
五、工作原理
HTTP協(xié)議采用請(qǐng)求/響應(yīng)模式,客戶端向服務(wù)器發(fā)送一個(gè)請(qǐng)求報(bào)文,然后服務(wù)器響應(yīng)請(qǐng)求。下面介紹一下一次HTTP請(qǐng)求的過(guò)程:
- 在瀏覽器中輸入
URL,并按下回車鍵 - 瀏覽器向
DNS服務(wù)器請(qǐng)求解析該URL中的域名對(duì)應(yīng)的IP地址(如果是IP請(qǐng)求,則不需要該步驟) - 解析出
IP后,根據(jù)IP和端口號(hào),和服務(wù)器建立TCP連接 - 瀏覽器向服務(wù)器發(fā)送請(qǐng)求,該請(qǐng)求報(bào)文作為
TCP三次握手的第三個(gè)報(bào)文發(fā)送給服務(wù)器 - 服務(wù)器做出響應(yīng),把數(shù)據(jù)發(fā)送給瀏覽器
- 通信完成,斷開
TCP連接 - 瀏覽器解析收到的數(shù)據(jù)并顯示
六、HTTPS簡(jiǎn)介
HTTPS是安全的HTTP通道,即在HTTP通信中加入了SSL層(當(dāng)前版本是TLS1.2),通信的數(shù)據(jù)被加密了,防止被竊取,具體的通信流程如下:

HTTPS使用的加密方式結(jié)合了對(duì)稱加密和不對(duì)稱加密的特點(diǎn),在保證安全的情況下,又提高了傳輸效率。HTTP和HTTPS的區(qū)別如下:
1.https協(xié)議需要到ca申請(qǐng)證書,一般免費(fèi)證書很少,需要交費(fèi)。
2.http的信息是明文傳輸,https 則是具有安全性的ssl加密傳輸協(xié)議。
3.http和https用的端口不一樣,前者是80,后者是443。
4.http的連接很簡(jiǎn)單,是無(wú)狀態(tài)的;HTTPS協(xié)議是由SSL+HTTP協(xié)議構(gòu)建的可進(jìn)行加密傳輸、身份認(rèn)證的網(wǎng)絡(luò)協(xié)議,比http協(xié)議安全
至此,HTTP的介紹就告一段落了,當(dāng)然HTTP協(xié)議的內(nèi)容還是很多的,本文只是涉及了常用的部分,文中不足之處,還請(qǐng)各位看官指出。(文中圖片來(lái)自互聯(lián)網(wǎng),如有侵權(quán),請(qǐng)告知,我怕賠不起)
參考資料