前端面試必懂的 - http 網路知識

sandy_anqi發表於2019-03-06

一.一個完整的 HTTP 連線

一個完整的 http 連線有五個步驟;

1.TCP 三次握手

該部分表示 A 向 B 發出請求,建立連線

(一)第一次握手(A->B):

A 向 B 傳送一個 TCP 的包,帶上了標誌 SYN,表示要建立一個連線,並指明包開始的序列號 seq,以後傳送的位元組編號都是以這個作為起點,並告知能接收的最大報文段長度 mms 為 1460,一般 mms 都是1460.

(二)第二次握手(B->A):

B 進行回覆,傳送一個 SYN + ACK 的報文段,表示同意建立連線

(三)第三次握手(A->B)

A 收到 SYN 之後,向 B 傳送一個 ACK,完成三次握手。

三次握手

為什麼 TCP 握手要三次?

TCP 前兩次的握手就可以確定對方的存在,第三次的握手是為了防止已失效的連線請求報文段突然又傳送到B,因而產生錯誤。 異常情況:假設 A 向 B 傳送了一個連線請求報文段,但是因為某些網路結點長時間滯留,以致延遲到連線請求釋放後的某個時間才到達 B。本來這是一個早已失效的請求報文段,但 B 收到此失效請求報文段後,就誤認為 A 又發出一次新的連線請求。於是就想 A 發出確認報文段。若,只有兩次握手,B 就是一隻建立連線,浪費資源。但如果有 第三次握手,B 一直都沒有接收到 A 發回來的第三次確認,就會自動斷開連線。

2.接收視窗

(一) TCP 的流量控制

通過滑動視窗機制進行流量控制

(二) TCP 的擁塞控制

  • 慢開始和擁塞避免
  • 快速重傳和快恢復演算法

此處簡寫接收視窗的控制機制

3.傳送資料

此部分省略吧~

4.關閉連線 四次揮手

(一)第一次揮手

當 A 覺得不用再請求資料時,等過了 30S 就要把請求連結關閉,向 B 傳送一個 FIN 的報文。

為什麼需要等 30s 才關閉呢?

因為 HTTP 1.1 版本之後的請求的 Connection:keep-alive 欄位的影響。因為同一個域可能要請求多個資源,如果每請求一次就關閉連線。下次請求時,又要建立 TCP 連線,是浪費資源的。

(二)第二次揮手

B 收到 A 發來的包後,向 A 傳送一個 ACK ,這時連線處於半關閉狀態,A 不能向 B 傳送資料,但是 B 可以向 A 傳送資料。

(三)第三次揮手

當 B 覺得沒有資料需要傳送時,向 A 傳送 FIN

(四)第四次揮手

A 收到 B 發來的結束連線請求,向 B 傳送一個 ACK ,此時連線完全關閉。然後主動關閉方 A 進入 TIME_WAIT (時間等待)狀態。

四次揮手

5.TIME_WAIT

TIME_WAIT 時間為 2MSL(maximum segmentt live-time),標準建議為 2 分鐘,但是實際運用中,2 分鐘太長了。

為什麼 A 在 TIME_WAIT 狀態下必須等待 2MSL ?

原因有二,一是:為了保證 A 最後傳送的 ACK 能夠成功到達 B 端。二是:防止上一節“三次握手”處提及到的“已失效的連線請求報文段”出現在本連結中。A 在傳送完最後一個 ACK 報文段後,再經過 時間 2MSL 後,就可以使本連線持續的時間內所產生的所有報文段都從網路中消失。


http/https 協議

1.http協議格式

  • request: request-line(由三部分組成 1.請求方法;2.請求地址;3.請求協議和版本) head body
  • response response-line(由三部分組成 1.協議和版本,狀態碼,狀態文字) head body

2.http狀態碼和狀態文字

  • 1XX 臨時迴應,表示客戶端請繼續
  • 2XX
    • 200 請求成功
  • 3XX 表示請求的目標有變化,希望客戶端進一步處理
    • 301&302 永久性和臨時性跳轉
    • 304 客戶端快取沒有跟新
  • 4XX
    • 403 沒有許可權
    • 404 頁面不存在
    • 418 it‘s a teapot
  • 5XX 服務端錯誤
    • 500 伺服器錯誤
    • 503 伺服器端暫時性錯誤,可以一會再試

3.http request Head 請求頭

  • accept 瀏覽器端接受的格式
  • accept-encodind 瀏覽器端接受的編碼格式
  • accept-language 瀏覽器端接受的語言
  • cache-control 控制快取的時效性
  • connection 連線方式 如果是 keep-alive 且瀏覽器支援,會用複用連線
  • host http訪問使用的域名
  • if-modified-since 上次訪問時的更改時間,如果伺服器端認為此後沒有更新,則會返回304
  • if-none-match 上次訪問的etag,通常是頁面的資訊摘要
  • user-agent 客戶端表示
  • cookie 客戶端快取的餓cookie 字串

4.http response head 響應頭

  • cache-control 快取控制 用於通知各級快取儲存的時間
  • connection 連線方式
  • content-encoding 內容編碼 通常是 gzip
  • content-length 內容長度 ,瀏覽器用於判斷內容是否已經結束
  • content-type 內容型別,所有請求網頁的都是 text/html
  • date 當前伺服器時間
  • eatg 頁面的資訊摘要,用於判斷是否需要重新到伺服器取回頁面
  • expires 過期時間,用於判斷下次請求是否要到伺服器端取回頁面
  • keep-alive 保持連線不斷時需要的一些資訊,如 timeout,max
  • last-modifiled 上次修改時間
  • server 伺服器軟體型別
  • set-cookie 設定cookie
  • via 服務端的請求鏈路

5.http request body 響應體

  • application/json
  • application/x-www-form-ulencoded
  • multipart/form-data
  • text/html

6.https

https 有兩個作用:

  • 一是用於確定請求的目標伺服器的身份;
  • 二是保證傳輸的資料不會被網路中間竊聽或者篡改,即是防止中間人攻擊。

(一)中間人攻擊方式

1.域名汙染

由於我們訪問一個域名時需要先進行域名解析(在沒有快取的情況下),即向 DNS 服務請求某個域名的 IP 地址。在經過 DNS 的中間鏈點可能會被搶答,返回一個錯誤的 IP 地址,這個 IP 地址有可能就指向中間人的機器。

2.APR 欺騙

廣域網的傳輸用的是 IP 地址,而在區域網裡面是用實體地址,例如路由器需要知道連線它的裝置的實體地址才能傳送資料包,當路由器不知道對應的實體地址時,會通過 ARP 廣播,向所有裝置查詢某個 IP 地址對應的實體地址。由於這個區域網內的所有機器都會受到這個包,所以這時候就可以欺騙路由器。

安全

xss (cross site scripting)

是一種網站應用程式的安全漏洞,它允許惡意者將程式碼注入到網頁上。通過修改 html 結點或者執行 js 程式碼來攻擊網站

防禦:

  1. 轉義輸入輸出的內容,設定白名單
  2. CSP content-security-policy,通過在 http header 中開啟 CSP。本質上,也是設定白名單,通過規範瀏覽器只能夠執行特定來源的程式碼

只允許載入本站資源 Content-Security-Policy: default-src ‘self’

只允許載入 HTTPS 協議圖片Content-Security-Policy: img-src https://*

允許載入任何來源框架Content-Security-Policy: child-src 'none'

  1. cookie 設定 httpOnly

CSRF (cross site request forgery)

簡單地說,就是利用使用者的登入態發起惡意請求

防禦

  1. get 請求不對資料進行修改
  2. 不讓第三方網站訪問到 cookie

可以對 Cookie 設定 sameSite ,該屬性設定 Cookie 不隨著跨域請求傳送。

  1. 阻止第三方網站請求

通過驗證 referer 來判斷請求是否為第三方網站發起

  1. 請求時,附帶驗證資訊,如驗證碼或者 token

伺服器下發一個隨機的 token,每次請求都將 token 帶上,伺服器判斷 token 是否有效。

(未完待續 ...)

歡迎大家在評論區共同探討 ~ 
希望寫的文章能夠為同在坑裡的你我解答一點點的疑問~


參考文獻

  1. 《計算機網路》(第七版)謝希仁著
  2. 《高效前端》李銀城著


相關文章