从浏览器原理分析 preload 和 prefetch 是如何控制资源加载的
preload 和 prefetch 的作用和区别
- preload
- 是一种在页面加载过程中提前加载关键资源的方法
- 通过在页面头部以 的方式引入资源
- 告诉浏览器哪些资源是页面加载过程中需要优先加载的
- 适用于当前页面需要的资源,可以帮助加快关键资源的加载速度,提高首屏渲染性能。
- prefetch
- 是一种在浏览器空闲时提前加载未来可能需要的资源的方法
- 通过在页面头部以 的方式引入资源
- 告诉浏览器哪些资源是未来页面可能会使用到的可以在浏览器空闲时提前加载这些资源,以减少未来页面加载时的延迟
- 适用于未来可能会被访问到的资源,可以在一定程度上提高用户的后续页面加载速度。
- 总结概述
preload
和prefetch
都是用来提高网站性能的技术preload
是针对当前页面的关键资源进行提前加载的prefetch
则是针对未来可能会被访问到的资源提前加载- 正确使用
preload
和prefetch
可以有效地优化页面性能和用户体验。
浏览器加载资源过程
首先看一个问题:当我们在浏览器地址栏输入网址并点击回车之后,浏览器肯定需要加载一批相关的资源,包括但不限于
html,css,js,image
等文件,那么浏览器是按照什么顺序加载这些资源的呢?
其实在浏览器加载资源时,内部会经历以下步骤:
- 将所有需要加载的资源进行分类
- 根据浏览器相关的安全策略,来决定资源的加载权限。
- 对各个资源的加载优先级进行计算和排序。
- 最后,根据加载优先级顺序来加载资源。
第一步:资源分类
例如:chrome浏览器常用的资源分类,如下表所示:
类型 | 介绍 |
---|---|
kMainResource | 主资源,html页面文件资源就属于该类型 |
kImage | 各种图片资源 |
kCSSStyleSheet | 层叠样式表css资源 |
kScript | 脚本资源,例如js资源 |
kFont | 字体资源,例如网页中常用的字体集.woff资源 |
kRaw | 混合类型资源,最常见的ajax请求就属于这类资源 |
kLinkPrefetch | HTML5页面的预读取资源,例如dns-prefetch |
kMedia | 多媒体资源,video or audio都属于该类资源 |
第二步:安全策略检查
网页安全政策(即
CSP
)是由浏览器提供的一种白名单制度。开发者通过配置,来告诉浏览器各类外部资源的加载和执行限制,来提高网页的安全性。
最常用的应用就是通过限制非信任域名脚本的加载来预防XSS攻击。可以通过两种方式来配置CSP
。
- 通过页面
HTTP
请求头的Content-Security-Policy
字段来限制。 - 通过
<meta>
标签来设置。<meta>
是以key-value
的方式来进行配置的。有以下作用:- 用于预防
XSS
<meta http-equiv="Content-Security-Policy" content="script-src 'self'; style-src www.ym1.com www.ym2.com;">
script-src
代表脚本资源style-src
代表样式资源- '
self
’代表只信任当前域名下的外来资源,其他域下的资源全部会被拦截 www.ym1.com www.ym2.com
代表信任这两个域名下的资源- 整体来看:脚本资源只信任本域下的资源,样式资源,除了本域还会加载
www.ym1.com www.ym2.com
两个域名下的资源
- 用于站点请求协议升级过渡(
http转https
)<meta http-equiv="Content-Secur****ity-Policy" content="upgrade-insecure-requests">
upgrade-insecure-requests
:表示升级所有非安全请求- 当加了这个
meta
标签以后,浏览器会将https
页面中的所有http
请自动升级到https
- 使用场景:当我们需要进行全站
http
转https
改造时,对于原有的大量http资源会直接强制以https
或wss
等SSL
加密形式发送请求而不会报错
- 用于阻止
Mixed Content
混合内容(<meta http-equiv="Content-Security-Policy" content="block-all-mixed-content">
Mixed Content
)就是在https
站点中,进行的http
请求。这类在安全链接中混合了非安全请求内容就叫混合内容。出现这类请求时,我们可以在浏览器控制台中找到对应的警告信息,如下图所示。
混合内容会降低HTTPS
网站的安全性和用户体验。不过浏览器对于可能对安全性造成较大威胁的资源类型的混合模式请求都会直接拦截报错。对于安全性要求极高的网站,可以通过上面的标签来阻止所以类型的非安全链接请求。
- 用于预防
第三步:资源优先级计算
资源的优先级被分为5级。从浏览器内核方面,5级分别为:VeryHigh、High、Medium、Low、VeryLow
,浏览器的资源优先级有以下计算过程:
- 根据资源的类型来设定默认优先级。 对于每一类资源浏览器都有一个默认的加载优先级规则
html、css、font
这三种类型的资源优先级最高- 然后是
preload
资源(通过<link rel=“preload">
标签预加载)、script、xhr
请求; - 接着是图片、语音、视频;
- 最低的是
prefetch
预读取的资源。
- 根据实际规则,对优先级进行调整
初始优先级设置好以后,浏览器会根据资源的实际属性和位于文档中的位置等方面,对优先级进行调整,来确定出最终的加载优先级顺序。对于几个常见资源类型的调整规则如下:- 对于
XHR
请求资源- 将同步XHR请求的优先级调整为最高。
- XHR请求可以分为同步请求和异步请求,浏览器会把同步请求的优先级提升到最高级,以便尽早获取数据、加快页面的显示。
- 对于图片资源
- 会根据图片是否在可见视图之内来改变优先级。
- 图片资源的默认优先级为
Low
。现代浏览器为了提高用户首屏的体验,在渲染时会计算图片资源是否在首屏可见视图之内,在的话,会将这部分视口可见图片(Image in viewport
)资源的优先级提升为High
。
- 对于脚本资源
- 浏览器会将根据脚本所处的位置和属性标签分为三类,分别设置优先级。
- 首先,对于添加了
defer/async
属性标签的脚本的优先级会全部降为Low
。 - 然后,对于没有添加该属性的脚本,根据该脚本在文档中的位置是在浏览器展示的第一张图片之前还是之后,又可分为两类。在之前的(标记
early
)它会被定为High
优先级,在之后的(标记late
)会被设置为Medium
优先级。
- 对于
第四步:加载资源
按照上面计算的安全策略和优先级来加载或阻塞资源
根据浏览器加载资源策略,如何做页面优化
利用关键请求链
- 什么是关键请求链
- 可视区域渲染完毕(首屏),并对于用户来说可用时,必须加载的资源请求队列,就叫做关键请求链。
- 了解关键请求链后,我们可以通过关键请求链,来确定优先加载的资源以及加载顺序,以实现浏览器尽可能快地加载页面。
- 如何找到关键请求链
- 通过
LightHouse
插件获取关键请求链中的关键js和css资源。
LightHouse
可以生成一个报告,里面包含了有关该页面性能的全方面报告和建议。其中有关关键请求链的报告如下图所示:
- 通过浏览器控制台查看各个请求的优先级 打开
Chrome
控制台,切换到Network tab
下,就可以查看资源的优先级(Priority
)。
如果没有Priority
一栏,可以右键在下拉菜单中勾选Priority
即可。如下图所示:
- 通过
- 如何优化关键请求链
- 利用以上描述的
Preload和Prefetch
。
注意:Preload和Prefetch
有一个关键缺点:兼容性较差 - 第二种:利用
LocalStorage
。
可以利用LocalStorage
来对部分请求的数据和结果进行缓存,省去发送http请求所消耗的时间,从而提高网页的响应速度。兼容性较好,移动端应用已经十分广泛。
- 利用以上描述的