写了这么久前端,你知道浏览器原理吗?

最近发现了一篇不错的文章,分享给你们,对于写了好久前端代码但不了解浏览器原理的朋友应该有很大帮助。前端

  这是一篇全面介绍 Webkit 和 Gecko 内部操做的入门文章,是以色列开发人员塔利·加希尔大量研究的成果。在过去的几年中,她查阅了全部公开发布的关于浏览器内部机制的数据(请参见资源),并花了不少时间来研读网络浏览器的源代码。程序员

她写道:web

  在 IE 占据 90% 市场份额的年代,咱们除了把浏览器当成一个“黑箱”,什么也作不了。可是如今,开放源代码的浏览器拥有了过半的市场份额,所以,是时候来揭开神秘的面纱,一探网络浏览器的内幕了。呃,里面只有数以百万行计的 C++ 代码...数据库

  塔利在她的网站上公布了本身的研究成果,可是咱们以为它值得让更多的人来了解,因此咱们在此从新整理并公布。后端

  做为一名网络开发人员,学习浏览器的内部工做原理将有助于您做出更明智的决策,并理解那些最佳开发实践的个中原因。尽管这是一篇至关长的文档,可是咱们建议您花些时间来仔细阅读;读完以后,您确定会以为所费不虚。保罗·爱丽诗 (Paul Irish),Chrome 浏览器开发人员事务部浏览器

简介服务器

  网络浏览器极可能是使用最广的软件。在这篇入门文章中,我将会介绍它们的幕后工做原理。咱们会了解到,从您在地址栏输入 google.com 直到您在浏览器屏幕上看到 Google 首页的整个过程当中都发生了些什么。网络

咱们要讨论的浏览器框架

  目前使用的主流浏览器有五个:Internet Explorer、Firefox、Safari、Chrome 浏览器和 Opera。本文中以开放源代码浏览器为例,即 Firefox、Chrome 浏览器和 Safari(部分开源)。根据 StatCounter 浏览器统计数据,目前(2011 年 8 月)Firefox、Safari 和 Chrome 浏览器的总市场占有率将近 60%。因而可知,现在开放源代码浏览器在浏览器市场中占据了很是坚实的部分。工具

浏览器的主要功能

  浏览器的主要功能就是向服务器发出请求,在浏览器窗口中展现您选择的网络资源。这里所说的资源通常是指 HTML 文档,也能够是 PDF、图片或其余的类型。资源的位置由用户使用 URI(统一资源标示符)指定。

  浏览器解释并显示 HTML 文件的方式是在 HTML 和 CSS 规范中指定的。这些规范由网络标准化组织 W3C(万维网联盟)进行维护。 
  多年以来,各浏览器都没有彻底听从这些规范,同时还在开发本身独有的扩展程序,这给网络开发人员带来了严重的兼容性问题。现在,大多数的浏览器都是或多或少地听从规范。

  浏览器的用户界面有不少彼此相同的元素,其中包括:

  • 用来输入 URI 的地址栏

  • 前进和后退按钮

  • 书签设置选项

  • 用于刷新和中止加载当前文档的刷新和中止按钮

  • 用于返回主页的主页按钮

  奇怪的是,浏览器的用户界面并无任何正式的规范,这是多年来的最佳实践天然发展以及彼此之间相互模仿的结果。HTML5 也没有定义浏览器必须具备的用户界面元素,但列出了一些通用的元素,例如地址栏、状态栏和工具栏等。固然,各浏览器也能够有本身独特的功能,好比 Firefox 的下载管理器。

浏览器的高层结构

  浏览器的主要组件为:

  • 用户界面 - 包括地址栏、前进/后退按钮、书签菜单等。除了浏览器主窗口显示的您请求的页面外,其余显示的各个部分都属于用户界面。

  • 浏览器引擎 - 在用户界面和呈现引擎之间传送指令。

  • 呈现引擎 - 负责显示请求的内容。若是请求的内容是 HTML,它就负责解析 HTML 和 CSS 内容,并将解析后的内容显示在屏幕上。

  • 网络 - 用于网络调用,好比 HTTP 请求。其接口与平台无关,并为全部平台提供底层实现。

  • 用户界面后端 - 用于绘制基本的窗口小部件,好比组合框和窗口。其公开了与平台无关的通用接口,而在底层使用操做系统的用户界面方法。

  • JavaScript 解释器。用于解析和执行 JavaScript 代码。

  • 数据存储。这是持久层。浏览器须要在硬盘上保存各类数据,例如 Cookie。新的 HTML 规范 (HTML5) 定义了“网络数据库”,这是一个完整(可是轻便)的浏览器内数据库。

图:浏览器的主要组件。

 

  值得注意的是,和大多数浏览器不一样,Chrome 浏览器的每一个标签页都分别对应一个呈现引擎实例。每一个标签页都是一个独立的进程。

呈现引擎

  呈现引擎的做用嘛...固然就是“呈现”了,也就是在浏览器的屏幕上显示请求的内容。

  默认状况下,呈现引擎可显示 HTML 和 XML 文档与图片。经过插件(或浏览器扩展程序),还能够显示其它类型的内容;例如,使用 PDF 查看器插件就能显示 PDF 文档。可是在本章中,咱们将集中介绍其主要用途:显示使用 CSS 格式化的 HTML 内容和图片。

呈现引擎

  本文所讨论的浏览器(Firefox、Chrome 浏览器和 Safari)是基于两种呈现引擎构建的。Firefox 使用的是 Gecko,这是 Mozilla 公司“自制”的呈现引擎。而 Safari 和 Chrome 浏览器使用的都是 Webkit。

  Webkit 是一种开放源代码呈现引擎,起初用于 Linux 平台,随后由 Apple 公司进行修改,从而支持苹果机和 Windows。有关详情,请参阅 webkit.org。

主流程

  呈现引擎一开始会从网络层获取请求文档的内容,内容的大小通常限制在 8000 个块之内。

  而后进行以下所示的基本流程:

图:呈现引擎的基本流程。

 

  呈现引擎将开始解析 HTML 文档,并将各标记逐个转化成“内容树”上的 DOM 节点。同时也会解析外部 CSS 文件以及样式元素中的样式数据。HTML 中这些带有视觉指令的样式信息将用于建立另外一个树结构:呈现树。

  呈现树包含多个带有视觉属性(如颜色和尺寸)的矩形。这些矩形的排列顺序就是它们将在屏幕上显示的顺序。

  呈现树构建完毕以后,进入“布局”处理阶段,也就是为每一个节点分配一个应出如今屏幕上的确切坐标。下一个阶段是绘制 - 呈现引擎会遍历呈现树,由用户界面后端层将每一个节点绘制出来。

  须要着重指出的是,这是一个渐进的过程。为达到更好的用户体验,呈现引擎会力求尽快将内容显示在屏幕上。它没必要等到整个 HTML 文档解析完毕以后,就会开始构建呈现树和设置布局。在不断接收和处理来自网络的其他内容的同时,呈现引擎会将部份内容解析并显示出来。

主流程示例

图:Webkit 主流程

图:Mozilla 的 Gecko 呈现引擎主流程 

  从上图能够看出,虽然 Webkit 和 Gecko 使用的术语略有不一样,但总体流程是基本相同的。

  Gecko 将视觉格式化元素组成的树称为“框架树”。每一个元素都是一个框架。Webkit 使用的术语是“呈现树”,它由“呈现对象”组成。对于元素的放置,Webkit 使用的术语是“布局”,而 Gecko 称之为“重排”。对于链接 DOM 节点和可视化信息从而建立呈现树的过程,Webkit 使用的术语是“附加”。有一个细微的非语义差异,就是 Gecko 在 HTML 与 DOM 树之间还有一个称为“内容槽”的层,用于生成 DOM 元素。咱们会逐一论述流程中的每一部分:

解析 - 综述

  解析是呈现引擎中很是重要的一个环节,所以咱们要更深刻地讲解。首先,来介绍一下解析。

  解析文档是指将文档转化成为有意义的结构,也就是可以让代码理解和使用的结构。解析获得的结果一般是表明了文档结构的节点树,它称做解析树或者语法树。

示例 - 解析 2 + 3 - 1 这个表达式,会返回下面的树:

 

图:数学表达式树节点

语法

  解析是以文档所遵循的语法规则(编写文档所用的语言或格式)为基础的。全部能够解析的格式都必须对应肯定的语法(由词汇和语法规则构成)。这称为与上下文无关的语法。人类语言并不属于这样的语言,所以没法用常规的解析技术进行解析。

解析器和词法分析器的组合

  解析的过程能够分红两个子过程:词法分析和语法分析。

  词法分析是将输入内容分割成大量标记的过程。标记是语言中的词汇,即构成内容的单位。在人类语言中,它至关于语言字典中的单词。

  语法分析是应用语言的语法规则的过程。

  解析器一般将解析工做分给如下两个组件来处理:词法分析器(有时也称为标记生成器),负责将输入内容分解成一个个有效标记;而解析器负责根据语言的语法规则分析文档的结构,从而构建解析树。词法分析器知道如何将无关的字符(好比空格和换行符)分离出来。

图:从源文档到解析树

  解析是一个迭代的过程。一般,解析器会向词法分析器请求一个新标记,并尝试将其与某条语法规则进行匹配。若是发现了匹配规则,解析器会将一个对应于该标记的节点添加到解析树中,而后继续请求下一个标记。

  若是没有规则能够匹配,解析器就会将标记存储到内部,并继续请求标记,直至找到可与全部内部存储的标记匹配的规则。若是找不到任何匹配规则,解析器就会引起一个异常。这意味着文档无效,包含语法错误。

 

若是有对前端感兴趣前端程序员,能够来咱们的web前端技术学习群的哦618522268。会送前端的零基础教程噢!

写在最后:

不少人都知道我是学全栈的,都天真的觉得我有全套的前端、网页制做等视频学习资料。我想说大家是对的,个人确有前端的全套视频资料。

 

未完待续...

ps:写给正在努力学习的朋友们,一个100行的代码调试均可能会让程序员遇到不少挫折,因此,面对挫折,咱们永远不能低头。

相关文章
相关标签/搜索