手把手教你完成前端性能建模

1. 性能工程几个定律

帕累托法则

常说的"二八法则",很多时候,大约20%的因素操控80%的局面。

应用场景 内容 意义
应用程序的使用 80%的用户使用集中在大约20%的功能 对常用的模块进行充分优化
程序代码开发时间的分配 80%的开发时间花费在最精髓的20%的代码 合理规划好开发时间
程序代码的维护 80%的代码演进和改动发生在20%的代码上 对最常改动的少部分代码尽量熟悉
程序代码的修正和纠错 80%的错误发生在20%的代码上 代码修复要重点修复最容易产生bug的代码
客户流量的时间分布 80%的流量将在总时间段的特定20%内发生 设计和部署,充分考虑访问峰值和空闲时段
程序代码的优化 80%的时间是运行大约20%的代码 发现少数重点代码并做优化

理解80%和20%是相对的概念,实际比例不一定跟这个吻合。

阿姆达尔定律

处理器并行运算之后效率提升的能力,加速比用并行前的速度和并行后的速度之比来表示,表示效率提升情况。优先加速占用时间最多的模块,因为这样可以最大限度地提升加速比。

利特尔法则

在一个稳定的系统中,长期的平均客户人数(N)等于客户抵达速度(X)乘以客户在这个系统中平均处理时间(W),也就是说 N=XW。

  • 设计性能测试的环境:用户请求流量速度和每个请求的延时都要考虑。
  • 验证测试结果的正确性:在高低并发不同情况下响应速度可能不同。

2. 优化前需要了解的几件事

了解你的用户

通过埋点上报,数据收集,得到关于用户特征的统计信息

操作系统分布

可根据用户操作系统的分布。 举个例子:80%的用户使用windows访问系统,15%的用户使用MacOS,剩余为其他操作系统。

地区分布

国家地区分布,了解国内外用户的访问比例。可以是否做国际化、CDN部署海外站点等的决策依据。 举个例子:90%的用户都来自中国,10%的用户来自海外,其中海外的用户主要集中在欧洲。

浏览器分布和版本分布

开发时兼容浏览器版本和测试业务系统提供参考依据。举个例子:80%的用户都是使用Chrome浏览器,15%的用户使用Safari,需要重点针对Chrome和Safari浏览器。

基于以上所有信息,我们可以建立用户画像 :

90%的用户都是在中国,海外主要的用户是在美国,主要是在Mac或者Windows的操作系统进行工作。使用的浏览器主要是Chrome、其次是Safari。

了解你的整体架构

前后端整体架构

前端页面架构

机房部署

前后端服务尽可能部署在同一机房,提升响应的速度。

3.明确性能优化目的,建立北极星指标

为什么要做性能优化,收益如何度量

性能要比竞争对手领先20%,才有可能被用户感知。

对于C端而言,可以从以下方面进行衡量:

  • 用户体验:提高网站或应用程序的加载速度和响应性,减少等待时间,提升用户体验和满意度。
  • 用户留存率:更好的用户体验通常会导致用户更倾向于留在网站或应用程序,减少用户的跳出率。
  • 转化率:快速加载的网页可以提高转化率,例如更多的订阅、购买或注册行为。
  • SEO优化:搜索引擎对快速加载的网页进行青睐,可能提升网站在搜索结果中的排名,吸引更多流量。
  • 节约成本:性能优化减少了服务器资源的使用,可能降低了运维成本和服务器费用。

对于B端,性能优化对于复购率的贡献率比较难以衡量,很少会因为性能而做出购买的决策,功能才是用户决策购买的最重要的因素。那有什么办法,可以相对量化对于用户产生的价值?个人的看法可以从两个方面进行分析(欢迎大家多多讨论):

  • 降本。CDN成本 = 节省带宽(包体积减少大小)* 9000元/Gbps(CDN收费)
  • 提效。节约成本 = 提升用户的时间效率 * PV * 人力平均成本

同时也为后面实现复杂功能,压榨性能空间,当性能特别好的时候,也可以作为产品的一个特性进行宣传。

以什么性能指标为北极星指标

分类 性能指标 含义解释
页面加载速度 FCP (First Contentful Paint) 首次内容渲染,表示浏览器首次渲染页面的时间点。
LCP (Largest Contentful Paint) 最大内容绘制,表示页面上最大的可见内容绘制完成的时间点。
TTI (Time To Interactive) 可交互时间,表示页面变得完全可交互的时间点。
用户交互 FID (First Input Delay) 首次输入延迟,用户首次与页面交互到浏览器实际响应交互的时间。
CLS (Cumulative Layout Shift) 累计布局位移,衡量页面内容在加载过程中的稳定性。
LongTask 长任务
FPS (Frames Per Second) 帧率,表示浏览器每秒渲染的帧数,用于衡量页面渲染的流畅程度。

结合你的业务实际去进行判断。

要优化哪些页面

如果有很多页面,需要确定优化的优先级,可以参考以下标准,结合自己的业务实际进行调整(如果有用户反馈某个页面很慢,影响到日常使用,那也是需要重点关注的页面)。

PV 使用频次
L1 级页面 PV 总量前 5% 的页面 使用频次前 5% 的页面
L2 级页面 PV 总量前 5%~70% 的页面 使用频次前 5%~70% 的页面
L3 级页面 PV 总量前 70%~100% 的页面 使用频次前 70%~100% 的页面

根据PV排名和使用频次进行优先级排行,根据资源投入决定优化先后顺序。除此之外,对于一些慢得比较离谱的页面(例如10s以上)也是一个优化重点,这种情况大概率是比较容易优化取得很大的优化效果。

系统性分析页面性能

准备工作

  • 确定设备型号和网络环境

    • 设备型号MacBook Pro(2018版,CPU: 2.2 GHz Intel Core i7, 内存: 16G)/'
  • 确定使用的测试环境:不同环境的接口返回速度和响应性能具有很大的差异

  • 测试冷启动情况下性能,需要勾选disable cache,防止缓存的干扰,有无缓存的情况下性能分析会有很大的不同。

  • 最好在无痕窗口进行试验,排除扩展插件对于页面的干扰,有些扩展插件对于页面性能有比较大的影响。

使用 Performance 分析页面加载全流程

  1. 点击录制

一般分析页面,点击reload按钮(图中1),直接等待分析结果出来就可以了。

但有些情况,例如

  • 刷新页面之后,需要手动触发才会出现我们想要分析的页面
  • 点击reload按钮后,在还没出现页面主体内容的时候,直接录制结束,导致performance没有分析整个过程

这时候我们需要需要点击record按钮(图中2),进行录制。

以某个网页为例,点击record进行记录。然后再调整起始时间轴来进行分析。

起点和终点的判断。

  • 一般起点为请求HTML模板的起点
  • 终点为主体内容展示:可以通过screenshot进行辅助判断。

2. 划分阶段

划分阶段有助于我们对整个页面加载的各个阶段有个整体的了解,对于后续优化。按照示例,大致可分为两个阶段

  • 主应用加载

    • 模板下载
    • 资源下载
    • JS解析和执行
  • 子应用加载和执行

    • 模板下载
    • 初始静态资源下载和执行
    • 全局公共接口请求
    • 页面渲染

关于图中的那些颜色块的含义:

  • 左侧线条代表从事件组"Connection Start"(包含在内)之前的所有事件,是在"Request Sent"之前的所有事件,但不包括"Request Sent"。
  • 条形图的浅色部分代表"Request Sent"和"Waiting (TTFB)"。
  • 条形图的深色部分代表"Content Download"。
  • 右侧线条表示主线程等待的时间。

network上先后顺序只是表现,要结合实际的业务代码去判断哪些请求是主路径上的。

可能出现的情况是,图中可能在某个时间段内只有个请求,但实际上这个请求并不会阻塞页面加载和渲染,很容易就被误导是这个原因导致。结合代码和main下面的执行任务综合起来看,才能够区分出这种情况。

注意看看是否有长任务,长任务执行的时候,会阻塞主进程的调用。也可以通过Call Tree等方式确定代码调用的位置来辅助定位。

包大小分析

有个原则:捡西瓜丢芝麻 ,重点优化体积比较大的包。可以使用www.npmjs.com/package/web... 来进行辅助分析

提供一些思路:

  • 移除旧的历史依赖
  • 查看初始化加载的问题
  • external基础库
  • 使用轻量的包进行替换

包体积的优化也能够减少js的执行时长

请求分析

接口可能存在不合理调用或者时序问题,分析业务接口的调用的先后顺序。

  • 接口时序

    • 串行改并行
    • 只调用初始渲染必须的接口
    • 历史遗留的多余接口可去除
  • 接口数量优化

    • 可合并,接口聚合
    • 老旧接口可下掉
    • 接口预请求
  • 接口耗时

    • 服务端进行优化
  • 接口并发请求:可并发的请求尽量并发

一些小技巧

  • performance导出Profile,可以多次回放
  • 注意线上和线下的接口耗时数据区别,可能会有坑。
  • 数据波动的解释:PV、UV的相关性指标辅助进行判断数据波动的原因

参考链接

相关推荐
吃杠碰小鸡23 分钟前
lodash常用函数
前端·javascript
emoji11111133 分钟前
前端对页面数据进行缓存
开发语言·前端·javascript
泰伦闲鱼35 分钟前
nestjs:GET REQUEST 缓存问题
服务器·前端·缓存·node.js·nestjs
m0_7482500340 分钟前
Web 第一次作业 初探html 使用VSCode工具开发
前端·html
一个处女座的程序猿O(∩_∩)O1 小时前
vue3 如何使用 mounted
前端·javascript·vue.js
m0_748235951 小时前
web复习(三)
前端
AiFlutter1 小时前
Flutter-底部分享弹窗(showModalBottomSheet)
java·前端·flutter
麦兜*1 小时前
轮播图带详情插件、uniApp插件
前端·javascript·uni-app·vue
陈大爷(有低保)1 小时前
uniapp小案例---趣味打字坤
前端·javascript·vue.js
m0_748236581 小时前
《Web 应用项目开发:从构思到上线的全过程》
服务器·前端·数据库