從瀏覽器地址欄輸入回車後會發生什麼?

前言

在前端面試中,往往會有一個非常經典的面試題,從瀏覽器地址欄輸入地址,並敲下回車後會發生什麼?這是一個非常寬泛、考察知識廣度和深度的題目。還記得最開始回答這個問題時,首先想到的是DNS解析-> 請求數據 -> HTML解析、CSS解析 -> 構造DOM樹 -> 構造渲染樹 -> 瀏覽器根據渲染樹進行渲染,將頁面展示到瀏覽器界面上。後來接觸了winter老師的重學前端的課程,對HTML、CSS解析又有了更深的認識,這個過程主要是通過詞法、語法分析來構造DOM樹和渲染樹。今天我想從瀏覽器入手來回答我們一開始的問題。

瀏覽器是多進程

不知道大家有沒有思考過這個問題,瀏覽器是多進程的,在Chrome瀏覽器中,設置->更多工具->任務管理器中,可以看到瀏覽器中有很多個進程。
在這裏插入圖片描述
可以看到這裏面有一個名叫瀏覽器的進程,一個GPU進程,兩個實用進程,多個標籤頁進程,多個擴展程序進程,這些進程分別是做什麼呢?下面我們來分析這些進程。

主進程

瀏覽器的主控進程,每個瀏覽器中僅有一個主控進程,對應上面截圖中的 瀏覽器進程。
主要負責:

  1. 網絡資源的下載;
  2. 頁面的展示與用戶交互;
  3. 協調各個進程,創建/銷燬頁面進程。
GUP進程

主要負責3D繪製,每個瀏覽器最多一個GPU進程。

渲染進程

這是瀏覽器每個TAB對應的進程,每一個TAB頁都是一個渲染進程,該進程負責HTML、CSS解析和DOM樹構造、渲染樹構造,計算元素位置等頁面渲染工作,以及JS腳本執行和事件處理過程。
這個進程是整個過程的核心處理過程,該進程中包括了多個線程來處理整個渲染過程。

GUI渲染線程
該線程主要做以下事情:
1. 解析HTML
2. 解析CSS
3. 構造DOM樹和SOM樹
4. 佈局和繪製

該線程與JS引擎線程是互斥的,當有JS引擎線程在執行時,該線程就會被掛起,所以當某個JS處理時間很長時,一般會出現頁面卡頓現象。

JS引擎線程

這個線程應該是我們比較熟悉的了,它是來執行我們的JS代碼的。這個過程可能會與時間處理線程、異步請求線程以及定時器觸發器線程並行進行。後面再整體舉例子來講。並且該線程是單線程的,所有其他線程的處理需等到該線程空閒時纔會執行。

事件處理線程

事件處理線程是實現事件循環的一個專門線程,主要是來處理像setTimeout、ajax請求、點擊事件等的專門的線程,爲了讓JS引擎線程專注得做一件事,該線程會維護一個事件隊列。
當有像上述的一些JS時,會在滿足條件後,將對應的任務放置到事件隊列中,直到JS引擎線程空閒時,纔會執行任務,執行任務的過程涉及到事件循環機制了。

異步請求線程

該線程應該就是來處理像Ajax一類的異步請求,若代碼中有異步請求的過程,瀏覽器會創建一個異步請求線程,該線程監聽XMLHTTPRequest對象的狀態,若狀態變更時有對應的回調函數,就會將回調函數給事件處理線程,事件處理線程將其放置到事件隊列中,等到JS引擎線程空閒時,按照事件循環機制執行。

定時器觸發器線程

該線程就是來處理setTimeout和setInterval這類操作了,若有這些過程,定時器線程會進行計時,當計時滿足條件之後,會將回調函數給事件處理線程,事件處理線程會將其放置到事件隊列中,等到JS引擎空閒時,按照事件循環機制執行。

第三方插件進程

該進程主要是擴展程序對應的進程,在擴展程序被啓用時,纔會有對應的進程。每種擴展程序對應一個插件進程。沒錯,上圖中的Vimium、windows Resizer和網頁截圖註釋是我瀏覽器中安裝的擴展程序。

瀏覽器各進程如何通信

知道了瀏覽器是多進程的,那麼瀏覽器各個進程是如何進行交互的呢?當我們打開瀏覽器,應該是主進程來接收的,那主進程是如何與每個TAB頁的渲染進程進行通信的,整個瀏覽器的處理流程是怎樣的?

當用戶從瀏覽器發起請求時:

  1. 瀏覽器主控進程請求頁面內容,然後通過一個RenderHost接口將信息發給渲染進程;
  2. 渲染進程通過Render接口拿到信息之後,進行一些解釋和處理,然後由GUI渲染線程進行渲染;
  3. 渲染線程主要來解析HTML、CSS以及構造DOM樹等,CSS資源的下載等需要主進程來進行網絡請求,也可能需要GPU進程來協助。當然,過程可能會遇到JS,此時也需要JS引擎線程來處理,如果有異步的任務,還需要事件處理線程來做。
  4. 當所有渲染工作做完之後,渲染進程會將結果反饋給瀏覽器主進程,主進程將結果進行繪製。

這應該就是在瀏覽器回車之後,瀏覽器的一系列操作,希望本文可以讓大家有個大概的瞭解和認識。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章