1. 程式人生 > >在瀏覽器中輸入URL並回車後發生了什麼?

在瀏覽器中輸入URL並回車後發生了什麼?

1、解析URL

在瀏覽器中輸入URL後,瀏覽器首先對拿到的URL進行識別,抽取出域名欄位。

URL(Universal Resource Locator):統一資源定位符。俗稱網頁地址或者網址。
在這裡插入圖片描述
80埠預設不顯示,“?” 到“#”之間跟著引數,多個引數使用“&”連線,“#”後面跟著錨。

2、DNS域名解析

DNS,域名系統,是一個把域名和IP對映的資料庫。
IP地址往都難以記住,但機器間互相只認IP地址,於是人們發明了域名,讓域名與IP地址之間一一對應,它們之間的轉換工作稱為域名解析,域名解析需要由專門的域名解析伺服器來完成,整個過程是自動進行的。

可以在瀏覽器中輸入IP地址瀏覽網站,也可以輸入域名查詢網站,雖然得出的內容是一樣的但是呼叫的過程不一樣,輸入IP地址是直接從主機上呼叫內容,輸入域名是通過域名解析伺服器指向對應的主機的IP地址,再從主機呼叫網站的內容。

DNS解析的步驟:
(1)查詢瀏覽器快取(瀏覽器會快取之前拿到的DNS 2-30分鐘時間),如果沒有找到
(2)檢查系統的hosts檔案(儲存了一些以前訪問過的網站的域名和IP的資料),如果沒有找到
(3)檢查路由器快取,如果沒有找到
(4)查詢本地伺服器快取,如果還沒有找到
(5)由本地域名伺服器依次向根域名伺服器、頂級域名伺服器、極限域名伺服器請求搜尋目標域名的IP
(6)獲取到IP地址

3、建立TCP連線(三次握手)

第一次握手,客戶端傳送一個帶有SYN標誌的請求給服務端等待確認,狀態變為syn-send
第二次握手,伺服器傳送一個帶有syn+ack的確認指令
第三次握手,客戶端收到確認指令並返回一個ACK確認資訊。
連線建立,可以傳輸資料了。
然後建立連線


為什麼要三次握手?
因為客戶端發出的連線請求有可能因為網路原因滯留了,並沒有丟失,有可能在連線釋放以後才到達服務端。這時B收到在傳送一個確認報文,由於這時客戶端沒有請求連線,所以不會迴應服務端的確認,也就不會建立連線。

4、瀏覽器發起HTTP請求

HTTP請求報文由請求行、請求頭、請求體組成。
請求行
請求方法、URL、HTTP協議及版本。

POST /user HTTP/1.1

請求頭:
包含一些請求資訊。

Accept:可接受的響應內容型別,如text/plain、image/jpeg…
Accepy-Language:響應內容的語言,如zh-CN
Content-Type:請求體的型別
Connection:客戶端想使用的連線型別,如Keep-Alive
Cache-Control:指定是否使用快取機制,如no-cache
Host:表示伺服器域名和監聽的埠號,如localhost:8088

空行

請求體:
GET方法中沒有,POST方法中用來傳遞引數。

5、服務端處理HTTP請求並響應

伺服器收到請求後,將收到的HTTP報文封裝成HTTP的請求物件,由不同的來處理然後把結果放在響應報文中一起返回給瀏覽器。

響應報文由響應行、響應頭、響應體組成。

響應行
伺服器HTTP協議版本,響應狀態碼,狀態碼的文字描述

HTTP/1.1 200 OK

響應頭
Access-Control-Allow-Origin:指定哪些網站可以跨域源資源共享
Allow:對於特定資源的有效動作
Cache-Control:通知從伺服器到客戶端內的所有快取機制,表示它們是否可以快取這個物件及快取有效時間。其單位為秒
Content-Range:如果是響應部分訊息,表示屬於完整訊息的哪個部分
Date:此條訊息被髮送時的日期和時間
Expires:指定一個日期/時間,超過該時間則認為此迴應已經過期
Last-Modified:所請求的物件的最後修改日期
Set-Cookie:設定HTTP cookie

響應體
需要返回的資料

6、瀏覽器解析渲染

(1) 首先當用戶輸入一個URL的時候,瀏覽器就會發送一個請求,請求URL對應的資源。
(2) 然後瀏覽器的HTML解析器會將這個檔案解析,並且構建成一棵DOM樹。
(3) 在構建DOM樹的時候,遇到JS和CSS元素,HTML解析器就會將控制權轉讓給JS解析器或者是CSS解析器。
(4) JS解析器或者是CSS解析器解析完這個元素時候,HTML又繼續解析下個元素,直到整棵DOM樹構建完成。
(5) DOM樹構建完之後,瀏覽器把DOM樹中的一些不可視元素去掉,然後與CSSOM合成一棵render樹。
(6) 接著瀏覽器根據這棵render樹,計算出各個節點(元素)在螢幕的位置,然後渲染到螢幕上去。

7、關閉TCP連線(四次揮手)

第一次揮手。客戶端傳送帶有FIN的終止請求。進入fin-wait
第二次揮手。服務端收到請求,先發送ACK確認資訊,然後等待剩餘的資料傳完。
第三次揮手。傳完後,服務端傳送FIN報文表示要關閉。進入close-wait
第四次揮手。客戶端收到後,向服務端傳送請求ACK表示連線斷開,之後會進入time_wait等待2ms以免ACK丟失重傳。服務端收到後關閉。

在這裡插入圖片描述
為什麼要四次揮手?
關閉時,伺服器收到關閉報文,不會立即關閉,先回復一個ACK報文。需要等到所有的服務端報文傳送完畢才會傳送FIN報文。

為什麼要有time_wait?
為了保證客戶端傳送的最後一個ACK能夠到達服務端。這個ACK可能丟失,然後服務端就會超時重傳這個FIN+ACK,A就可以在2ms內收到這個重傳的報文,然後A再重傳一次確認,然後都進入closed狀態。