<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          你不知道的 Webkit 內核(5000字,了解瀏覽器渲染原理)

          共 6001字,需瀏覽 13分鐘

           ·

          2020-11-20 02:04

          當下瀏覽器內核主要有 Webkit、Blink 等。本文分析注意是自 2001 年 Webkit 從 KHTML 分離出去并開源后,各大瀏覽器廠商魔改 Webkit 的時期,這些魔改的內核最終以 Chromium 受眾最多而脫穎而出。本文就以 Chromium 瀏覽器架構為基礎,逐層探入進行剖析。

          引子

          這里以一個面試中最常見的題目從 URL 輸入到瀏覽器渲染頁面發(fā)生了什么?開始。

          這個很常見的題目,涉及的知識非常廣泛。大家可先從瀏覽器監(jiān)聽用戶輸入開始,瀏覽器解析 url 的部分,分析出應用層協(xié)議 是 HTTPS 還是 HTTP 來決定是否經過會話層 TLS 套接字,然后到 DNS 解析獲取 IP,建立 TCP 套接字池 以及 TCP 三次握手,數據封裝切片的過程,瀏覽器發(fā)送請求獲取對應數據,如何解析 HTML,四次揮手等等等等。這個回答理論上可以非常詳細,遠比我提到的多得多。

          本文試圖從瀏覽器獲取資源開始探究 Webkit。如瀏覽器如何獲取資源,獲取資源時 Webkit 調用了哪些資源加載器(不同的資源使用不同的加載器),Webkit 如何解析 HTML 等入手。想要從前端工程師的角度弄明白這些問題,可以先暫時拋開 C++源碼,從瀏覽器架構出發(fā),做到大致了解。之后學有余力的同學再去深入研究各個底層細節(jié)。

          本文的路線循序漸進,從 Chromium 瀏覽器架構出發(fā),到 Webkit 資源下載時對應的瀏覽器獲取對應資源如 HTML、CSS 等,再到 HTML 的解析,再到 JS 阻塞 DOM 解析而產生的 Webkit 優(yōu)化 引出瀏覽器多線程架構,繼而出于安全性和穩(wěn)定性的考慮引出瀏覽器多進程架構。

          一. Chromium 瀏覽器架構

          Chromium瀏覽器架構

          (Chromium 瀏覽器架構)

          我們通常說的瀏覽器內核,指的是渲染引擎。

          WebCore 基本是共享的,只是在不同瀏覽器中使用 Webkit 的實現方式不同。它包含解析 HTML 生成 DOM、解析 CSS、渲染布局、資源加載器等等,用于加載和渲染網頁。

          JS 解析可以使用 JSCore 或 V8 等 JS 引擎。我們熟悉的谷歌瀏覽器就是使用 V8。比如比較常見的有內置屬性 [[scope]] 就僅在 V8 內部使用,用于對象根據其向上索引自身不存在的屬性。而對外暴露的 API,如 __proto__ 也可用于更改原型鏈。實際上 __proto__ 并不是 ES 標準提供的,它是瀏覽器提供的(瀏覽器可以不提供,因此如果有瀏覽器不提供的話這也并不是 b ug)。

          Webkit Ports 是不共享的部分。它包含視頻、音頻、圖片解碼、硬件加速、網絡棧等等,常用于移植。

          同時,瀏覽器是多進程多線程架構,稍后也會細入。

          在解析 HTML 文檔之前,需要先獲取資源,那么資源的獲取在 Webkit 中應該如何進行呢?

          二.Webkit 資源加載

          HTTP 是超文本傳輸協(xié)議,超文本的含義即包含了文本、圖片、視頻、音頻等等。其對應的不同文件格式,在 Webkit 中 需要調用不同的資源加載器,即 特定資源加載器。

          而瀏覽器有四級緩存,Disk Cache 是我們最常說的通過 HTTP Header 去控制的,比如強緩存、協(xié)商緩存。同時也有瀏覽器自帶的啟發(fā)式緩存。而 Webkit 對應使用的加載器是資源緩存機制的資源加載器 CachedResoureLoader 類。

          如果每個資源加載器都實現自己的加載方法,則浪費內存空間,同時違背了單一職責的原則,因此可以抽象出一個共享類,即通用資源加載器 ResoureLoader 類。Webkit 資源加載使用了三類加載器:「特定資源加載器,資源緩存機制的資源加載器 CachedResoureLoader 和 通用資源加載器 ResoureLoader」

          既然說到了緩存,那不妨多談一點。

          資源既然緩存了,那是如何命中的呢?答案是根據資源唯一性的特征 URL。資源存儲是有一定有效期的,而這個有效期在 Webkit 中采用的就是 LRU 算法。那什么時候更新緩存呢?答案是不同的緩存類型對應不同的緩存策略。我們知道緩存多數是利用 HTTP 協(xié)議減少網絡負載的,即強緩存、協(xié)商緩存。但是如果關閉緩存了呢?比如 HTTP/1.0 Pragma:no-cache 和 HTTP/1.1 Cache-Control: no-cache。此時,對于 Webkit 來說,它會清空全局唯一的對象 MemoryCache 中的所有資源。

          資源加載器內容先到這里。瀏覽器架構是多進程多線程的,其實多線程可以直接體現在資源加載的過程中,在 JS 阻塞 DOM 解析中發(fā)揮作用,下面我們詳細講解一下。

          三.瀏覽器架構

          瀏覽器是多進程多線程架構。

          對于瀏覽器來講,從網絡獲取資源是非常耗時的。從資源是否阻塞渲染的角度,對瀏覽器而言資源僅分為兩類:「阻塞渲染」如 JS 和 「不阻塞渲染」如圖片。

          我們都知道 JS 阻塞 DOM 解析,反之亦然。然而對于阻塞,Webkit 不會傻傻等著浪費時間,它在內部做了優(yōu)化:啟動另一個線程,去遍歷后續(xù)的 HTML 文檔,收集需要的資源 URL,并發(fā)下載資源。最常見的比如

          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                    <th id="afajh"><progress id="afajh"></progress></th>
                    无码一道本一区二区无码 | 超碰免费天天操天天干 | 亚洲无码中出乱伦内射 | 色综合久久鬼88888 | 在线国色天看一区一 |