文章目录
写在前面
前端性能优化的意义
- 提升用户体验
- 留住用户
- 提高网站的转化率
常见性能指标
- TTFB 页面加载的白屏时间
请求发出到请求响应的时间,通常取决于网络和服务器处理能力
- waterfall 瀑布图
- 横向代表资源的请求耗时
- 纵向代表资源阻塞情况
常见性能分析工具
- lighthouse 整体质量评估
- Chrome Dev 开发调试,性能评测
- Webpage Test 多测试地点,性能报告
Lighthouse 性能指标解读
FCP First Contentful Paint : 第一个可见元素绘制展现的时间
FCP 测量用户导航到页面后浏览器呈现第一段 DOM 内容所需的时间。图像,非白色
<canvas>
元素和页面上的 svg 被认为是 DOM 内容
FCP 指标
· 0-1.8S 绿色(快速)
· 1.8-3S 橙色(中等)
· 超过 3S 红色(慢)
FCP 重要优化手段
确保文本在 webfont 加载期间保持可见!
- 字体通常是需要一段时间才能加载完成的大文件,一些浏览器会在字体加载完成前隐藏文本,导致不可见文本闪烁—FOIT。因此比较好的做法是,通过设置
font-display:swap
在字体加载期间使用系统临时字体,以避免 FOIT
@font-face {
font-family: 'Pacifico';
font-style: normal;
font-weight: 400;
src: local('Pacifico Regular'), local('Pacifico-Regular'), url(https://fonts.gstatic.com/s/pacifico/v12/FwZY7-Qmy14u9lezJ-6H6MmBp0u-.woff2) format('woff2');
font-display: swap; // 这个字体显示API指定字体的显示方式swap告诉浏览器使用该字体的文本应立即使用系统字体显示。一旦自定义字体准备就绪,它将替换系统字体
}
- 另外一种做法是使用资源预加载 preload ,以提高字体加载速度。通过预加载可选字体,防止布局转换和不可见文本闪烁 FOIT
<link rel="preload" href="/assets/Pacifico-Bold.woff2" as="font" type="font/woff2" crossorigin>
as="font" type="font/woff2"
属性会告诉浏览器将此资源作为字体下载,并帮助确定资源队列的优先级。crossorigin
属性说明是否应使用 CORS 请求获取资源,因为字体可能来自不同的域。如果不设置此属性,浏览器将忽略预加载的字体。
通过预加载,浏览器知道它需要提前下载这个文件。需要注意的是,如果使用不当,预加载可能会对未使用的资源发出不必要的请求,从而导致性能损耗。
TTI Time to Interactive 可交互时间 测量页面需要多长时间才能响应用户的交互
如果王者加载时间超过 3S,超过 50% 的用户会放弃网站!
测量 TTI 很重要,因为有些网站以牺牲交互性为代价优化内容可见性。这可能会造成一个令人沮丧的用户体验:网站似乎已经准备好了,但是当用户试图与之交互时,什么都没有发生。
TTI 指标
· 0-3.8S 绿色(快速)
· 3.9-7.3S 橙色(中等)
· 超过 7.3S 红色(慢)
TTI 优化手段
一个对 TTI 影响特别大的改进是推迟或删除不必要的 JS 工作。
- 最有效的办法是进行代码拆分 搜索 SplitChunksPlugin 以了解详细的解决方案;
- 其次是减少主线程的工作比如使用 web worker,减少布局抖动带来的回流和重绘;减少 JS 的执行时间。
Speed Index 速度指数
速度指数衡量内容在页面加载期间的可视化显示速度。
Speed Index 性能指标
· 0— 3.4S 绿色(快速)
· 3.4—5.8S 橙色(中等)
· 超过 5.8S 红色(慢)
Speed Index 优化手段
- 减少主线程工作量
- 减少 JS 执行时间
- 确保文本 web font 加载期间可见
TBT Total Blocking Time 总阻塞时间
TBT 测量页面被阻止响应用户输入(例如鼠标点击、屏幕点击或按下键盘)的总时间。总和是首次内容绘制和互动时间之间所有长时间任务的阻塞部分之和。任何执行时间超过 50 毫秒的任务都是长任务。50 毫秒后的时间量是阻塞部分。例如,如果 Lighthouse 检测到一个 70 毫秒长的任务,则阻塞部分将为 20 毫秒。
TBT 性能指标
· 0—200 ms 绿色(快速)
· 200—600 ms 橙色(中等)
·超过 600 ms 红色(慢)
TBT 优化手段
· 代码拆分减少 JS 负载
· 删除未使用的 JS 代码
· 有效加载第三方 JS
LCP Largest Contentful Pain
LCP 测量视口中最大的内容元素何时呈现到屏幕上。这大约是当用户可以看到页面的主要内容时。
LCP 性能指标
· 0—2.5 S 绿色(快速)
· 2.5—4 S 橙色(中等)
· 超过 4 S 红色(慢)
LCP 优化手段
LCP 主要受 4 个因素影响:
- 缓慢的服务器响应速度
- JS 和 CSS 渲染阻塞
- 资源加载 时间
- 客户端渲染
-
使用 PRPL 模式做到及时加载
PRPL 是四个英文单词的首字母缩写,它描述了一种可以提高网页加载速度和交互性的模式
- 推送 (Push) (或 预加载 )最重要的资源。
- 尽快渲染 (Render) 初始路线。
- 预缓存 (Pre-cache) 剩余资产。
- 延迟加载 (Lazy load) 其他路线和非关键资产。
-
优化关键渲染路径
-
优化 CSS
-
优化图像
-
优化网页字体
-
优化 JS
CLS Cumulative Layout Shift 意外布局偏移
CLS 测量整个页面生命周期内发生的所有意外布局偏移中最大一连串的 布局偏移分数 。
为了提供良好的用户体验,网站应该努力将 CLS 分数控制在 0.1 或以下
RAIL 性能评测模式
RAIL 模型解读
-
R --> Response :响应 ( 响应控制在100ms内 )
-
A --> Animation : 动画 (在10ms内生成一帧)
-
I --> Idle : 空闲(最大程度增加主线程空闲时间)
-
L --> Load :加载(在1S内呈现内容,3G中等设备5S内可交互)
Response
如果用户点击了一个按钮,你需要保证在用户察觉出延迟之前就得到反馈。无论是表单控制还是执行动画,只要有输入,这个原则都适用。如果没有在合理的时窗内完成响应,也就是 采取动作和得到响应之间出现了断层 ,用户将会察觉到这个延迟。
响应的速度根本上来说取决于输入的延迟,输入的延迟存在于:指甲触到屏幕玻璃和实际像素到达屏幕之间。你有没有过这样的经历:轻触到某种东西,结果它没有给出任何反应,接着你就会质疑自己那个东西是否真的接收到你的轻触。这种自我怀疑的场景就是我们想要避免的!
响应的主要交互是:
- tapping(轻触) – 当用户轻触或者点击一个按钮或者图标时(比如,轻触菜单图标打开一个抽屉导航)。
要得到响应式的回应,我们需要:
- 在首次收到输入时,在100毫秒内得到回应。
- 理想情况下,收到的回应就是最终结果。但如果最终结果还需要花更长的时间得到,那也要给用户一个“加载中”的标识,或是颜色的变更,告诉用户“本产品已经接收到了指令,还在处理中”,不至于让用户自我怀疑
Animation
动画现在是应用的一大支柱,从滚动到视图变化,都有动画的身影。我们要明确在这段时间里能做些什么,因为用户可能常常是直接操作,帧率的改变很容易被察觉到。但是用户想要的只是流畅的响应而已。
动画包含了以下概念:
- 视觉动画
这个包括了动画的开始和退出,状态改变时的动画,还有加载标识。 - 滚动
当用户开始滚动页面,页面出现猛动的情况。 - 拖拽
当我们需要对用户的拖拽交互在100毫秒以内做出响应时,比如平移地图或者缩放屏幕时,我们需要依赖动画。
要合理地动画,每一帧动画要 在10毫秒内完成 ,才能达到60FPS(1000ms/60 ~= 16.6 ms)。
IDLE
要制作响应迅速动画精良的应用通常需要比较长的工时。Optimistic UI模式利用这个技术达到了很好的效果。并非所有工作都要在 response 阶段或者 load 阶段完成:评论引导、组件初始化、数据检索和排序和分析数据的送都不是需要立刻传达给用户的,所以可以在浏览器空闲的时候再处理这些任务。
要想合理地应用浏览器空闲时间,最好把时间以 50 毫秒为单位分组。为什么要这么做呢?在上文里也提到的,用户做出动作后,应用应该在 100 毫秒内给出响应,不应该出现一个模板渲染 2 秒之久。
LOAD
页面加载时间是最常见的性能话题。对用户来说最先看到的内容应该是最有意义、最先被加载出来的。接着页面要持续响应用户,绝对不允许出现在滚动页面、轻触或者看动画的时候卡顿。特别是当多个页面使用同一个线程的时候,要实现这样的目标真的很困难。
想要尽快将页面加载出来,我们需要把最需要传达的内容在 1 秒内渲染出来。超过 1 秒钟,用户的注意力就会被分散,当前执行的任务将有中断感。要达到在 1 秒内渲染完毕的目标,我们要优先考虑关键渲染路径,将所有不需要在加载时处理的任务延迟到浏览器空闲时再处理(或根据需求拦加载)。
WebPageTest_使用手册
WebPageTest 简介
浏览器、网络环境、访问位置测试。
一个免费开源的在线性能评测网站,支持IE,FireFox、Chrome,其使用真正的浏览器(IE和Chrome等)与真实的消费者连接速度,可以从全球多个地点运行免费网站速度测试;同时,也可以运行简单的测试或执行高级测试,包括多步骤事务、视频捕获、内容阻塞等等;将依据测试结果提供丰富的诊断信息,包括资源加载瀑布图,页面速度优化检查和改进建议,会给每一项内容一个最终的评级。
进入网站后,首页如下,WebpageTest主要分四个功能模块:Advanced Testing、simple Testing、Visual Comparison、Traceroute,我们只要关注Advanced Testing就好了。
使用步骤
-
由上图中,在1处输入要测试的URL,即网址。
-
在2处选择地址(Test Location),如下图,下拉选择就好,该功能异常强悍,可以选择安卓,iOS,PC端等设备,以及不同国家地区等。
-
在3处选择所支持的浏览器
补充:点击Advanced Setting下拉可以进行高级设置,不过我们一般选择默认就好
-
设置完成,点击START TEST,开始测试
开始测试
- 以百度网站(www.baidu.com)为例进行测试
测试进行中,页面左上角可以看到我们前面进行的设置参数。静等测试结果出来就好。
测试结果参数说明
看结果前先说下主要的测试的主要指标数据
- First Byte Time
适用对象:访问页面的第一字节时间(后端处理+重定向)
检查内容:目标时间包括DNS寻址时间+建立连接时间(Socket) + SSL认证时间 + 100ms。当超过目标时间每100ms时, 性能评定将降低一个等级
- Keep-Alive
适用对象:同一个域名下多个页面对象使用了同一个连接(Socket)
检查内容:响应头文件包含"Keep-Alive"的指令或者在给定的主机中多个对象中使用同一个连接
- GZIP Text
适用对象:工具会将MIME 类型为"text/" 或"java*"的所有对象
检查内容:检查Transfer-encoding来看是否为GZIP,如果不是则结果中会提供说明该文件是压缩过以及提供压缩比率(因此一个文件可以节省30%的大小,通过压缩即产生了源文件70%大小的文件)
- Compress Images
适用对象:JPEG图片
检查内容:对比使用photoshop质量选择为50后的文件大小,尺寸超出10%为达标,10%~50%为警告,超出50%为不达标,总体评分为图片重压缩后占原文件的百分比
- Use Progressive JPEGs
适用对象:所有JPEG图片
检查内容:检查每个JPEG图片文件并计算分数,分数为图片的压缩比(压缩文件大小/原文件大小)
- Cache Static
适用对象:符合以下的情况的任意的非html对象数据,这个工具会将MIME类型为"text/",“java"或者"image/”,此类没有明确标明过期时间(0或者-1),cache-controlheader设置为private,non-store 或者non-cachepragma header 设置为no-cache
检查内容:存在一个”Expires“ header(而不是0或者-1),或者设置cache-control: max-age并设置为一个小时或超过一个小时。当过期时间设置小于30天,将评定为警告
- Use A CDN
适用对象:所有静态的非HTML内容(css, js 以及图片)
检查内容:检查是否托管在一个已知的CDN上(CName映射到一个已知的CDN网络上).超过整体页面80%为静态资源时,则需要考虑使用CDN,将静态资源托管在CDN上,你可以从这里知道当前已知的CDN
具体实例结果
因是长页面,进行多个截图展示
a. Summary
说明:左上角是设置的测试信息,右上角提供了原始数据下载,有具体的数据分析,有测试网页的截图以及测试视频回放。各种详细的数据还可以点击链接进去查看。还会提供多次重复测试的结果,可通过重复试验进行对比数据。
b. Details 详细的细节数据
c. Connection view / Waterfall View
d. Request Details
e. Request Headers
f. Screenshot
g. Request Map
写在最后
前端性能优化是一门很深的学问涉及到许多方面的内容,是前端人必须要掌握的技能。本文作为前端性能优化系列的第一篇只是简单介绍了常见的性能优化指标和相关的性能优化工具。后续文章将从编码技巧、资源压缩、字体图片优化、webpack等几个方向详细介绍前端性能优化常见方法,欢迎大家收藏关注,一起学习。
- 内容预告