如何快速掌握HTTP協議?
HTTP 協議極其龐雜,它影響著瀏覽器、爬蟲、代理伺服器、防火牆、CDN、Web 容器、微服務等諸多方面,自身的規範卻並不統一,所要面對的各類軟體的新舊版本也同時存在於網路上。在這種情況下,如果對 HTTP 沒有一個深入的理解,就很容易被各種各樣的網路問題難倒。
那麼,如何才能快速掌握HTTP協議呢?
在我看來,需要從以下四個方面入手:
- 工欲善其事,必先利其器,首先我們先要掌握好抓包及相關的工具,這樣在分析各種網路協議時也就更加得心應手。
- 先從架構入手,搞清楚 HTTP 協議到底想解決什麼問題,面臨哪些非功能性的約束,又是怎樣一步步發展變遷至今的。
- 熟悉協議格式,對隧道或者正向代理下的 URI 格式、對多表述包體和不定長包體的傳輸格式要了解,對 DNS 的 QUESTION/ANSWER 也要了解。
- 掌握應用場景,跨域訪問與同源策略到底在糾結什麼?代理伺服器上的共享快取如何精細化控制?
先給大家分享我整理的 HTTP 學習知識圖譜,你可以收藏起來,時不時地拿出來對照:
下面,我們來一一詳述這四個方面。
1、用好工具
學好HTTP協議,至少要用到下面4個工具:
1.1 Chrome Network抓包面板
這個工具有4個優點:
- 快速分析HTTP請求
- 便捷解除安裝TLS/SSL內容
- 可協助分析頁面載入效能
- 方便分析websocket內容
該工具包含5個面板,在過濾器的Filter輸入欄中還支援複雜的屬性過濾,在請求列表中可以看到請求的上下游,亦能看到每個請求的時間分佈。
1.2 telnet
這個小工具主要用於構造原始的應用層協議,幫助我們理解HTTP實際在網路中傳輸的格式是什麼樣的。
1.3 curl
telnet有2個問題:
1、太過繁瑣,每次要輸入完整的請求。實際我們可能只是想改一下方法或者某個HEADER頭部。
2、不支援HTTPS,不支援包體壓縮,導致無法向某些站點發起請求。
而curl完美解決了這些問題。它也用於構造定製化的HTTP請求,並可以分析HTTP響應頭部或者包體。
1.4 Wireshark
這是學習完整Web協議棧的必備工具,我們可以在伺服器端用tcpdump抓包後,在視覺化的Wireshark上便捷分析。
Wireshark功能極為強大:
- 既支援BPF捕獲過濾器,也支援分析時的顯示過濾器;
- 通過流跟蹤或者會話圖示,我們可以輕鬆的以session會話為單位進行分析;
- 通過可配置的著色規則,但以不同的色彩幫助我們輕鬆找出有問題的報文;
- 通過報文的標註及匯出,以及檔案的合併、時間的平移,可以輕鬆將多臺機器上的抓到的報文放在一起分析對比;
- 既可以通過Packet Detail中看到每層報文解析出的可讀值,也能在Packet Byte中看到二進位制流。
- 支援報文統計,對大量HTTP報文的分析非常方便!
2、理解架構
要理解HTTP的架構,需要從以下4個方面入手:
2.1 HTTP協議想解決什麼問題?
HTTP協議設計之初用於解決人與機器間的通訊,所謂“B/S架構”中的瀏覽器是我們必須考慮進的因素。
因此,HTTP協議需要傳輸超媒體資料(包括圖片、視訊等大粒度資料)。
當然,現在許多物聯網中的裝置也在使用HTTP協議,所以,它也在解決機器與機器間的通訊。
當然,網路爬蟲也是HTTP協議要面對的問題,robots.txt這樣的規範也應運而生。
2.2 HTTP協議面對哪些非功能性約束?
主要包括以下5個方面:
- 高可擴充套件性,因為它需要面對全世界使用者群體以及數十年以上的壽命
- 低門檻,既有使用門檻也包括開發門檻,JavaApplet的式微與Javascript的如日中天就是極好的例證
- 分散式環境下的大粒度資料傳輸
- internet下無法控制的負載以及種類版本繁多的元件
- 向前相容,HTTP/1.1中的許多特性都需要照顧到還有僅支援HTTP/1.0的代理伺服器在網際網路上執行
2.3 遵循的架構設計方案是怎樣的?
HTTP/1.1是完全遵循REST架構設計,而REST架構主要包含以下4個子架構:
- LCS:空間上分層的客戶端伺服器,因此我們才有了隧道、代理、閘道器、CDN、負載均衡等產品;
- CSS:無狀態的客戶端伺服器,因此我們才有了Request/Response請求模式,才要求cookie頭部或者URL不能超過4K等。
- COD:按需程式碼,即將程式碼從伺服器移至客戶端再執行,今天的前端生態都是基於此架構下而生的Javascript衍伸的。
- $:快取,HTTP元件中無處沒有快取,共享快取、私有快取,沒指明快取時限還要預估一個快取過期值。
2.4 HTTP協議特性有哪些?
首先,我們需要理解它在OSI概念模型的哪一層,它又是處在TCP/IP體系的什麼位置。
其次,我們可以從上述架構中推匯出它的定義:一種無狀態的、應用層的、以請求/應答方式執行的協議,它使用可擴充套件的語義和自描述訊息格式,與基於網路的超文字資訊系統靈活的互動!
3、熟悉協議格式
學習HTTP協議格式時,應從以下3個方面入手:
3.1 擴充巴科斯-瑙爾正規化:ABNF元語言
元語言可用於描述協議格式,而ABNF就嚴謹定義了HTTP的格式。
ABNF並不複雜,只需要我們花10分鐘即可學會,它包括操作符和核心規則2大部分,這裡不再列出。
3.2 HTTP協議格式
掌握HTTP協議格式需要理清一個樹狀知識圖,參見本文末尾我整理的HTTP知識圖譜。
3.3 DNS協議格式
我們需要掌握3個方面的知識:
- DNS報文是基於UDP的,它的通用格式是固定的,需要理解各欄位含義
- Questions部分需要重點看QNAME域名是如何編碼的,以及QTYPE的含義
- Answers部分欄位更多,特別是對NAME及RDATA部分的偏移表示法要有所瞭解
4、掌握應用場景
HTTP的應用場景極其廣泛,下面我列出常見的9個場景,在協議格式中提到的各方法、響應碼、頭部、包體編碼方式都與具體場景相關。
4.1 內容如何協商
響應式協商由於RFC規範不明少有使用,而主動式協商關於語言、編碼、媒體型別等是我們日常打交道的常見方式。
4.2 FORM表單如何提交
表單提交雖然有3種編碼方式,但最常用的還是boundary分隔的多表述共存於單一包體的方式,waf防火牆必須考慮如何應用這種包體內的SQL注入攻擊。
4.3 Range請求的使用
傳輸大檔案所用到的斷點續傳和多執行緒下載,都需要使用Range規範,為防止多請求下載過程中伺服器端更新的情況,還引入條件請求If-Range。
4.4 Cookie與Session的設計
Set-Cookie中有許多屬性,既有限制有效期的expires-av、max-age-av,也有限制使用範圍的domain-av、path-av,還有限制協議的secure-av或是限制使用物件的httponly-av。
這種種限制都在針對瀏覽器使用cookie是否安全,而同時為了便利性瀏覽器也支援第三方cookie,這更是為廠商蒐集使用者資訊提供了方便。
4.5 瀏覽器同源策略與跨域請求
同源策略是瀏覽器所做的限制,如果我們直接基於網路庫處理響應是不受此限制的。所以,這個同源策略的有效性非常依賴瀏覽器的實現。當然,同源策略中不包含防範CSRF攻擊,伺服器通常基於token策略解決CSRF攻擊。
安全與便利是必須權衡取捨的,為了增加便利性,必須允許AJAX的跨域請求,於是CORS便誕生了。
4.6 條件請求
條件請求不只可應對多執行緒下載時的資源中途變數,也可針對多人協作的wiki系統生效,同時也能用於快取更新。實際在Restful API設計中它大有發揮餘地。
4.7 共享快取與私有快取
當下的網際網路上快取無處不在,即使伺服器上沒有配置某些資源可以快取,瀏覽器也在想盡辦法預估出一段時間快取資源。因為,快取能夠極大的提升使用者體驗、降低網路負載!能夠控制快取的HTTP頭部非常多,它不只控制快取的有效期,也在控制快取依據的關鍵字。
4.8 重定向的應用
關於重定向我們需要從2個維度4個象限去理解:可更改方法 | 不可更改方法、可快取|不可快取
這便引出了301、302、303、307、308這5種不同的響應狀態碼。
4.9 網路爬蟲
爬蟲無處不在,遠不只久遠的搜尋引擎爬蟲,當下在出行(例如12306火車票或者亞航)、電商、社交(新浪微博)等都廣受爬蟲騷擾,爬蟲不只爬取資訊,還模擬人類製造行為,例如許多搶票機、殭屍粉都如此。而另一方面,為了歡迎google/baidu的爬蟲,又誕生了各種SEO策略及教程,還有許多利用PageRank漏洞提升關鍵詞排名的商家在以此盈利。所以,理解爬蟲的工作方式也是非常重要的。
當然,HTTP應用場景遠不止這些,但徹底掌握這些場景將使我們完全理解HTTP協議中常見的方法、頭部、響應碼等等。
HTTP 協議是 Web 協議裡非常重的一塊,作為程式設計師,無論你是前後端工程師,還是運維測試,如果 想面試更高的職位,或者要站在更高的角度去理解技術業務架構,並能在問題出現時快速、高效地解決問題,Web 協議一定是你繞不過去的一道坎。 熟練掌握各種常用 Web 協議,可以幫你在工作中輕鬆應對各種網路難題。
基於此,我和極客時間合作推出了 《Web 協議詳解與抓包實戰》 視訊課, 完全從實戰出發,在關鍵場景中結合抓包工具進行實戰分析,為你深入淺出地講解常見 Web 協議涉及到的核心知識,並徹底掌握這些協議。