20170407快速理解HTTP協(xié)議
4月份給自己挖一個(gè)爬蟲(chóng)系列的坑冬阳,從理論到實(shí)踐猪钮,讓大家不僅知其然而且知其所以然。希望能做到深入淺出述雾。以爬蟲(chóng)為主線街州,涉及HTTP 協(xié)議、正則表達(dá)式玻孟、爬蟲(chóng)框架Scrapy唆缴、消息隊(duì)列、數(shù)據(jù)庫(kù)等內(nèi)容黍翎。訂閱公眾號(hào)「Python之禪」面徽,獲取最新干貨。
爬蟲(chóng)是一個(gè)模擬瀏覽器進(jìn)行 HTTP 請(qǐng)求的過(guò)程匣掸。
HTTP協(xié)議是什么趟紊?
你瀏覽的每一個(gè)網(wǎng)頁(yè)都是基于 HTTP 協(xié)議呈現(xiàn)的,HTTP
協(xié)議是互聯(lián)網(wǎng)應(yīng)用中旺聚,客戶端(瀏覽器)與服務(wù)器之間進(jìn)行數(shù)據(jù)通信的一種協(xié)議织阳。協(xié)議中規(guī)定了客戶端應(yīng)該按照什么格式給服務(wù)器發(fā)送請(qǐng)求,同時(shí)也約定了服務(wù)端返回的響應(yīng)結(jié)果應(yīng)該是什么格式砰粹。
只要大家都按照協(xié)議規(guī)定方式發(fā)起請(qǐng)求和返回響應(yīng)結(jié)果唧躲,任何人都可以基于HTTP協(xié)議實(shí)現(xiàn)自己的Web客戶端(瀏覽器、爬蟲(chóng))和Web服務(wù)器(Nginx碱璃、Apache等)弄痹。
HTTP 協(xié)議本身是非常簡(jiǎn)單的。它規(guī)定嵌器,只能由客戶端主動(dòng)發(fā)起請(qǐng)求肛真,服務(wù)器接收請(qǐng)求處理后返回響應(yīng)結(jié)果,同時(shí) HTTP
是一種無(wú)狀態(tài)的協(xié)議爽航,協(xié)議本身不記錄客戶端的歷史請(qǐng)求記錄蚓让。
HTTP 協(xié)議是如何規(guī)定請(qǐng)求格式和響應(yīng)格式的呢?換言之讥珍,客戶端按照什么格式才能正確發(fā)起 HTTP 請(qǐng)求呢历极?服務(wù)端按照什么格式返回響應(yīng)結(jié)果客戶端才能正確解析?
HTTP 請(qǐng)求
HTTP 請(qǐng)求由3部分組成衷佃,分別是請(qǐng)求行趟卸、請(qǐng)求首部、請(qǐng)求體,首部和請(qǐng)求體是可選的锄列,并不是每個(gè)請(qǐng)求都需要的图云。
請(qǐng)求行
請(qǐng)求行是每個(gè)請(qǐng)求必不可少的部分,它由3部分組成邻邮,分別是請(qǐng)求方法(method)竣况、請(qǐng)求URL(URI)、HTTP協(xié)議版本饶囚,以空格隔開(kāi)帕翻。
HTTP協(xié)議中最常用的請(qǐng)求方法有:GET、POST萝风、PUT、DELETE紫岩。GET方法用于從服務(wù)器獲取資源规惰,90%的爬蟲(chóng)都是基于GET請(qǐng)求抓取數(shù)據(jù)。
請(qǐng)求 URL 是指資源所在服務(wù)器的路徑地址泉蝌,比如上圖的例子表示客戶端想獲取 index.html 這個(gè)資源歇万,它的路徑在服務(wù)器 foofish.net的根目錄(/)下面。
請(qǐng)求首部
因?yàn)檎?qǐng)求行所攜帶的信息量非常有限勋陪,以至于客戶端還有很多想向服務(wù)器要說(shuō)的事情不得不放在請(qǐng)求首部(Header)贪磺,請(qǐng)求首部用于給服務(wù)器提供一些額外的信息,比如User-Agent 用來(lái)表明客戶端的身份诅愚,讓服務(wù)器知道你是來(lái)自瀏覽器的請(qǐng)求還是爬蟲(chóng)寒锚,是來(lái)自 Chrome 瀏覽器還是 FireFox。HTTP/1.1規(guī)定了47種首部字段類型违孝。HTTP首部字段的格式很像 Python 中的字典類型刹前,由鍵值對(duì)組成,中間用冒號(hào)隔開(kāi)雌桑。比如:
因?yàn)榭蛻舳税l(fā)送請(qǐng)求時(shí)喇喉,發(fā)送的數(shù)據(jù)(報(bào)文)是由字符串構(gòu)成的,為了區(qū)分請(qǐng)求首部的結(jié)尾和請(qǐng)求體的開(kāi)始校坑,用一個(gè)空行來(lái)表示拣技,遇到空行時(shí),就表示這是首部的結(jié)尾耍目,請(qǐng)求體的開(kāi)始膏斤。
請(qǐng)求體
請(qǐng)求體是客戶端提交給服務(wù)器的真正內(nèi)容,比如用戶登錄時(shí)的需要用的用戶名和密碼制妄,比如文件上傳的數(shù)據(jù)掸绞,比如注冊(cè)用戶信息時(shí)提交的表單信息。
現(xiàn)在我們用 Python 提供的最原始API socket 模塊來(lái)模擬向服務(wù)器發(fā)起一個(gè) HTTP 請(qǐng)求
HTTP 響應(yīng)
服務(wù)端接收請(qǐng)求并處理后,返回響應(yīng)內(nèi)容給客戶端衔掸,同樣地烫幕,響應(yīng)內(nèi)容也必須遵循固定的格式瀏覽器才能正確解析。HTTP響應(yīng)也由3部分組成敞映,分別是:響應(yīng)行较曼、響應(yīng)首部、響應(yīng)體振愿,與 HTTP 的請(qǐng)求格式是相對(duì)應(yīng)的捷犹。
響應(yīng)行
響應(yīng)行同樣也是3部分組成,由服務(wù)端支持的 HTTP 協(xié)議版本號(hào)冕末、狀態(tài)碼萍歉、以及對(duì)狀態(tài)碼的簡(jiǎn)短原因描述組成。
狀態(tài)碼是響應(yīng)行中很重要的一個(gè)字段档桃。通過(guò)狀態(tài)碼枪孩,客戶端可以知道服務(wù)器是否正常處理的請(qǐng)求。如果狀態(tài)碼是200藻肄,說(shuō)明客戶端的請(qǐng)求處理成功蔑舞,如果是500,說(shuō)明服務(wù)器處理請(qǐng)求的時(shí)候出現(xiàn)了異常嘹屯。404表示請(qǐng)求的資源在服務(wù)器找不到攻询。除此之外,HTTP 協(xié)議還很定義了很多其他的狀態(tài)碼州弟,不過(guò)它不是本文的討論范圍钧栖。
響應(yīng)首部
響應(yīng)首部和請(qǐng)求首部類似,用于對(duì)響應(yīng)內(nèi)容的補(bǔ)充呆馁,在首部里面可以告知客戶端響應(yīng)體的數(shù)據(jù)類型是什么桐经?響應(yīng)內(nèi)容返回的時(shí)間是什么時(shí)候,響應(yīng)體是否壓縮了浙滤,響應(yīng)體最后一次修改的時(shí)間阴挣。
響應(yīng)體
響應(yīng)體(body)是服務(wù)器返回的真正內(nèi)容,它可以是一個(gè)HTML頁(yè)面纺腊,或者是一張圖片畔咧、一段視頻等等。
我們繼續(xù)沿用前面那個(gè)例子來(lái)看看服務(wù)器返回的響應(yīng)結(jié)果是什么揖膜?因?yàn)槲抑唤邮樟饲?024個(gè)字節(jié)誓沸,所以有一部分響應(yīng)內(nèi)容是看不到的。
從結(jié)果來(lái)看壹粟,它與協(xié)議中規(guī)范的格式是一樣的拜隧,第一行是響應(yīng)行宿百,狀態(tài)碼是200,表明請(qǐng)求成功洪添。第二部分是響應(yīng)首部信息垦页,由多個(gè)首部組成,有服務(wù)器返回響應(yīng)的時(shí)間干奢,Cookie信息等等痊焊。第三部分就是真正的響應(yīng)體HTML 文本。
至此忿峻,你應(yīng)該對(duì) HTTP 協(xié)議有一個(gè)總體的認(rèn)識(shí)了薄啥,爬蟲(chóng)的行為本質(zhì)上就是模擬瀏覽器發(fā)送HTTP請(qǐng)求,所以要想在爬蟲(chóng)領(lǐng)域深耕細(xì)作逛尚,理解 HTTP協(xié)議是必須的垄惧。
當(dāng)然 HTTP協(xié)議遠(yuǎn)不止這么一點(diǎn)內(nèi)容,也根本不可能用一篇文章就試圖把它全部講清楚黑低,我在這里也只是拋磚引玉赘艳,想深入了解HTTP的,可參考公眾號(hào)「Python之禪」推薦的延伸閱讀克握。
來(lái)源于網(wǎng)頁(yè)鏈接:http://www.toutiao.com/a6405711322420723970/?tt_from=mobile_qq&utm_campaign=client_share&app=news_article&utm_source=mobile_qq&iid=6927887776&utm_medium=toutiao_ios