Open lewenweijia opened 5 years ago
优化场景
「前端进阶」高性能渲染十万条数据(时间分片)
对于大量数据渲染的时候,JS运算并不是性能的瓶颈,性能的瓶颈主要在于渲染阶段
raf? -> 系统来决定cb的执行时间
setTimeout的分批渲染, raf的分批渲染
最终?: raf + documentFragment(保存在内存中的啊, 是DOM节点, 但并不是DOM树的一部分) 减少页面
回流
Event: mousemove/keydown | Timer Fired | Animation Frame Fired
开发网页? 用户体验 | 可访问性 | 安全性 => 跟呼吸一样自然和简单
以用户为中心的性能指标 User-centric Performance Metrics
拆分计算任务, 减少用户输入延迟(键盘/鼠标)
http2多路复用和server push的结合使用(一条流一个资源, 不需要显式请求资源, 服务器主动server push 推送)
一对多的流推送服务, 一个请求多个六推送
schedule to the next IdlePoint (协调调度到下一个空闲点)
http2: 多路复用, 请求优先级, 头部压缩, 服务端推送
h2? 啥都不变, 只是针对数据的传输格式做了重新定义
一方面完美地向下兼容, 对用户完全透明, 只会感觉到性能的提升
关键渲染路径(critical rendering path)
前置: 什么是关键渲染路径:阻塞页面的初始化渲染也就是FP/FCP的咯
控制三个变量的尽可能小化
个数: 减少个数 大小: 压缩大小 长度: 尽可能趁早加载关键资源, 减短路径长度
消除/使其变得不重要 => 压缩/优化, 最小化传输字节
避免不必要的缓存开销 versioned url for long-lived caching: 长时间缓存的版本化url的啊
对第三方的tree shaking, 还不如直接cdn化的呢
工程化/性能优化/安全
largish: 稍大的 <-- somewhat large
document.body.childNodes[0].appendChild(component());
浏览器区分资源还是通过url的
window/global/self <==> browser/node.js/serviceWorker 简单地将sw想象成一个中间件就好了的, 中间人, 中间代理
尝试去拉取并安装sw
事实: 网络能力和设备能力总是不对称的
对低端网络,传输大小至关重要 对CPU能力差的设备,解析、编译的时间十分重要 ==》 应该尽可能减低这两个指标的呢
两个指标:
保持其价值尽可能降低第三方脚本带来对我们网站的影响,
IntersectionObserver + + dataset IntersectionObserver + div + background-image
video标签视频加载的延迟?
video => gif muted autoplay loop
首屏中的关键img资源直接用标准的img更快的啊
。。。抵制js实现懒加载带来的性能诱惑陷阱
首屏线
首屏线 + 向下适当缓冲区 => IntersectionObserver(cb, { rootMargin:" "})
图片、视频延迟加载? 减少不必要的下载:
最大限度压缩所需下载量
压缩
。注释 + 空格移除
文本的数量进行计数压缩
基于文本资源的minified(html、css、js):
gzip =》 针对文本资源压缩友好, 70%. 图片?其他算法处理过了的,gzip微乎其微
minified =》2. gzip ====》 .min.js.zip
minified?: 需要用特定的工具针对特定的资源进行压缩:
1. js,移除注解、空格换行、变量名简化
2. css、移除注解、空格换行、重叠选择器合并
3. html、移除注解、空格换行
服务器开启gzip,是回报率很高的一项劳作的啊
gzip后,体积反而变得更大?原本就高度压缩的了,内容比gzip所依赖存储压缩信息的成本还高 =》 设置进行gzip的文件最小阈值
tree shaking的好处?:
减少网络传输大小
减少js的解析、编译时间。js文件拉下来之后,肯定执行一次的啊(伪main)
避免不必要的下载
通过压缩技术优化每个资源的传输编码
利用缓存完全否定RTT
自有资源和第三方资源: 该资源是否遵循性能的最佳做法?压缩、缓存
第三方资源成为我们的单点故障? =》 也就是该资源不可用的时候,影响我们网页的性能和用户体验
基于文本的资源 [html、css、js]、png
css像素和设备像素的对应关系: 1个css像素刚好对应1个设备像素 1个css像素对应多个设备像素
设备像素越丰富,展示的效果越细腻
如果使用光栅图片,那么设置srcset、picture =》 提供图片的多个变体
svg?也是基于文本的资源的啊,也应该剔除注释、元信息、minified、gzipped
浏览器为光栅图片(不管什么格式)的每个像素始终占据4个字节的内存(rgba四通道信息) 500 × 500的像素的光栅图片 =》 1m左右
图片的格式选择:
三个能力:动画、透明度、浏览器支持度 webp支持动画、也支持透明度,和gif相差只有浏览器的支持程度了
多数cdn都会提供自动化图片优化服务
图片仍然是网络暴涨的原因
嘿嘿嘿, 图片优化是个精细活啊。。。 webp也是google家发明的啊
link下进行preconnect一个cdn站点,tcp消耗,tls消耗
webpack的js代码优化?
1. 减少重复代码 -》optimizaiton.splitChunks.cacheGroups => 不断的抽取公共代码
2. 动态导入
webpack的optimization里面配置
1. 压缩器:minimizer[ new TerserPlugin({}) ]
2. 公共模块抽取设置:splitChunks.cacheGroups
嘿嘿,都是通过白名单的形式的啊
预提取和预加载 prefetch: 低优先级,浏览器空闲时,类RIC preload: 高优先级,不阻塞load时间情况下进行记载, 类raf
预提取总是地风险的, 不会浪费用户流量
预提取/预加载技术: dns-prefetch: renderer项目中大量使用 prefetch: 低优先级, 浏览器空闲 preload: 高优先级, 不堵塞load事件, 真正获取的时候网络进程直接走cache通道
webpack的optimization.splitChunks下的智能代码分割
最后来个资源提示的效果的
dns-prefetch
preconnect
prefetch
preload
性能优化?:
1. 资源加载优化
2. 渲染优化
页面具有高可交互性,并且运行顺滑: 用户输入(键盘、鼠标、touch滚动) 动画
滚动应该像手指的滑动一样快
高性能网站和应用?
下面因素需要保持一致以获取最大的页面流畅度:
浏览器渲染动画和页面的速率 《===》 设备屏幕的刷新率
来来来,研究下为啥会出现卡顿感。。。(我只是分享我的发现和总结) 页面卡顿感?: 浏览器的渲染(出图)速率跟不上设备屏幕刷新率
卡顿、===》 用户体验
我们在意的是用户体验的效果的啊
如果处于交互状态,完全是js领导化的啊
布局、绘制、合成
渲染优化?这项工作是要浏览器配合的呢
sticky scrolling, 粘黏滚动 => 页面滚动跟手指滑动一样的快的效果的啊 闪烁更新,flickering update
布局和绘制是可选的啊,在渲染流水线(rendering pipeline)里面 layout property: 不改变元素的几何属性, 就不走layout步骤的啊 => 几何属性? width/height/position(top, left)信息, 宽/高/位置
最后的最后再走合成路线, 将他们合并回来
paint-only属性举例: background-image, text color, shadow, background-color
这个页面有几个图层的呢, 需要通过compositor进行合并页面的啊 页面由图层进行组成的
渲染流水线的第一个阶段: 可以引起视觉变化的统一(js、css改变、webanimation api)
渲染流水线,除了第一阶段和最后一阶段,其他的都是可选的啊
文本资源?
1. minified
2. comrpess
3. acahe
关键渲染路径?:浏览器获取资源到将它们渲染成页面的整个流程
BIG DEAL
关键渲染路径
渲染流水线
资源优化
1. 移除不必要的代码
2. minify
3. compress
4. cache
``
1. 页面获取
2. 子资源获取
浏览器会干的事情,也是开发者预定好的那些事情的效果的啊
增量形式的HTML分发, incrementally HTML delivery
let's go to timeline and record
练习?探索时间线轨迹
grep location *, 命令行文件扩展符
一帧结束的标识:像素被绘制到屏幕就好了的啊
js当然需要在一帧的开头进行尽可能早的执行:
raf?make js code run at the right point of every frame`
raf?很棒的工具来进行动画的制作
浏览器是如何渲染一帧的:渲染流水线
在16ms的时间预算下, 任务可能会超时,浏览器自身也有一些内部任务
browser has housekeeping to do
16ms? 浏览器每一帧也有内部工作要做,所以6ms给浏览器作为时间预算,那么我们就只有10ms了的啊
js代码在占据渲染流水线的时间,至多3/4的啊
样式计算
布局计算
绘制
合成(图层管理)
js问啥要在渲染流水线的最前面?因为js会导致后面的任何一个渲染流水线子阶段重新执行的啊 可能导致很多工作redone 同时,也尽可能让js有更多的时间进行执行 。。。jQuery still use setTimeout for animation today
setTimeout的问题,v8引擎对对啥时候出图是没有感知的,傻傻的等timeout
raf,浏览器每次出帧的时候, 会自动去拿里面的东西
为什么React是RIC? 让更高优先级的用户输入和动画,可以流畅执行。而React的reconcilation任务属于CPU密集性,不属于高优先级任务,可以延缓
function animate() {
// Do something super rad here
requestAnimationFrame(animate);
}
requestAnimationFrame(animate)
raf, 最低版本IE9, setTimeout来作为polyfill的效果的啊。并不是一个理想的fallback,但是可以工作的啊
可怕的可怕的啊,JS的代码都跑在帧里面的正确时间的啊
need to fill all the work inside 16ms
need to fill all the work inside 16ms =》 js => style => layout => paint => composite 10-12ms的时间来跑js代码的情况的啊。。style => ... => composite这一段可以认为对开发者完全是 不透明的,是浏览器的housekeeping。浏览器提供两个逃生舱让我们可以参与渲染流水线的协调中来 分别是raf和ric的啊 raf:js代码可以
js代码很容易在一帧里面超出一开始的时间预算
framework/library? => they has their work to do ,而不是单单你写的那些代码了的啊。哈哈
timeline? 告诉js执行时间,哪个函数,在哪里
and interact with the site
long-running JavaScript
通过Performance来查找长时间运行的JS代码的啊 这里我们会多出许多额外的信息,来帮助我们进行调研查找 find bottleneck more easily
sort fn? actually the built-in one is great!
Performance下的各种形式的火焰图的效果和形式的啊。flame view
主线程和worker线程互不干扰, 但是可以相互通信
main: consumeData(result) postMessage(params) worker: dowork(data) postMessage(result)
web worker对跑长时间js的任务来说, 无限价值的形式的啊。
spawn出一个新的ww线程
async,乱序。不依赖其他脚本 + 不操作DOM
https://github.com/berwin/Blog/issues w3c webperf会员大佬博客 嗨,送你一张Web性能优化地图
问题
如何进行系统性地页面优化
浏览器多进程架构 | 渲染主线程 | GUI线程和JS线程执行互斥 | 单处理管道的多任务调度策略 「前端进阶」从多线程到Event Loop全面梳理 从浏览器多进程到JS单线程,JS运行机制最全面的一次梳理
俚语
页面优化
浅谈script标签中的async和defer