9月7日-8日,相约 2023 腾讯全球数字生态大会!聚焦产业未来发展新趋势! 了解详情
写点什么

300 毫秒分胜负:维基百科的总阻塞时间优化之道

作者 :Nicholas Ray

  • 2023-06-27
    北京
  • 本文字数:2598 字

    阅读完需:约 9 分钟

300毫秒分胜负:维基百科的总阻塞时间优化之道

大家有没有遇到过响应缓慢、卡顿崩溃的垃圾网站?遇上这类性能缺陷,脾气火爆的朋友往往果断选择:


  • 狂点鼠标;

  • 退出走人,拉低客源转化率;

  • 搜索引擎排名因此下降。

 

三年多来,维基百科的移动版网站也深受一段 JavaScript 代码的戕害。在低端手机上,这段 JS 代码的页面加载时间可能超过 600 毫秒,大大影响了用户的交互体验。

 

在本文中,我们将一同了解如何通过几个简单步骤,让任务执行时间有效缩短约 50%。

 

总阻塞时间:长任务的重要性

 

在 JS 执行方面,600 毫秒似乎并不是什么无法接受的问题。但我们不妨想象这样的场景:当这段 600 毫秒的 JS 代码开始执行时,用户恰好想在加载过程中单击某个按钮。因为特定时段内浏览器的主线程只能处理一个任务,所以用户必须等待以下步骤完成后才能获得操作反馈:

  1. JS 任务花 600 毫秒执行完毕

  2. 点击处理任务随后开始执行

  3. 浏览器执行必要的渲染步骤,最终更新页面内容

 


 长任务可能导致视觉更新延迟,拖慢点击程序的处理速度

 

每个步骤都需要消耗时间,而任何超过 100 毫秒的响应速度都会给用户带来非常明确的延迟感受。正因为如此,谷歌将一切耗时超过 50 毫秒的任务定性为“长任务”,认为其会影响页面对用户输入的响应。他们甚至专门为此制定了“总阻塞时间”(TBT)的指标。



这里有两个长任务(大于 50 毫秒)——分别耗时 80 毫秒和 100 毫秒

 

总阻塞时间是什么?


所谓总阻塞时间,是指浏览器主线程上全部长任务在首屏内容绘制(FCP)和响应时间(TTI)之间的阻塞部分的总和。换言之,“阻塞部分”代表着每个长任务超出 50 毫秒之外的时间消耗。

 

计算以下示例中的总阻塞时间:

 


  1. 80 毫秒任务比 50 毫秒基准多出 30 毫秒,因此带来了 30 毫秒的总阻塞时间。

  2. 30 毫秒的任务不构成阻塞时间,因为其小于 50 毫秒且不属于长任务。

  3. 100 毫秒的任务比 50 毫秒基准多出 50 毫秒,因此带来了 50 毫秒的总阻塞时间。

 

由于总阻塞时间对应每个长任务超过 50 毫秒部分的总和,所以示例中的最终结果是 30 毫秒+50 毫秒=80 毫秒。

 

在常规移动硬件上进行测试时,谷歌建议站点的总阻塞时间应小于 200 毫秒。但维基百科上一项任务的执行就可能超过 600 毫秒——相当于总体上限的 3 倍。

 

我们该如何改进性能?

 

如何降低总阻塞时间


要降低这项指标,我们需要:

  • 在首屏绘制和交互时间之间,减少主线程上的工作负载;

  • 在保证工作内容不变的情况下,将长任务拆分成多个不超过 50 毫秒的小任务。

 

本文主要侧重第一种解决思路。

 

步骤 1:删除不必要的 JS 代码


HTML 解析、绘制和垃圾收集都需要在主线程上运行,但引发总阻塞时间过长的罪魁祸首仍然是 JS 代码。毕竟有经验的前端开发者都知道,网站降速背后总有 JS 的身影。



 在分析维基百科的移动站点时,我发现_enable 方法占用了大部分执行时间。此方法负责对移动站点上的部分开展和折叠行为进行初始化。配置文件则显示,在_enable 方法中,对 jQuery .on("click")方法的调用同样速度很慢。



 这里的.on("click")调用负责向内容中的几乎所有链接附加点击事件侦听器,这样如果点击的链接包含哈希片段,相应的部分就会被展开。对于链接较少的短文章,这部分性能影响几乎可以忽略不计。但对于像“美国”这类的长词条,其内容可能包含超过 4000 个链接,因此在低端设备上的执行时间会超过 200 毫秒。

 

更糟糕的是,这种设计完全没有必要。侦听 haschange 事件的下游代码已经调用了与点击事件侦听器相同的方法。除非窗口位置已经指向链接目的地,否则点击链接会对 checkHash 方法调用两次——一次用于链接点击事件处理程序,另一次用于 hashchange 处理程序。



这种情况下,最好的方法当然是直接删除这个 JS 代码块,在几乎不影响主线程功能的前提下直接省下近 200 毫秒。

 

在分析过程中,请始终检查最耗时的部分,之后看看有没有能够优化或者删掉的代码。

 

经验之谈:加快网站速度的首选方法,永远是删除 JS 代码。

 

步骤 2:优化现有 JS 代码



另一项性能审查显示,initMediaViewer 方法需要约 100 毫秒的执行时间。此方法负责将点击事件侦听器附加到内容中的各个缩略图处,这样点击缩略图即可打开媒体查看器:



 与步骤 1 中的链接示例类似,这种向页面上各个缩略图附加事件侦听器的方法不利于性能扩展。

 

维基百科中的词条可能包含数千张相关图片。在这些多图页面上运行这段代码时,其执行时间可能超过 100 毫秒,必然增加页面的总阻塞时间。下面来看替代方法。

 

答案就是事件委托

 

事件委托是一种强大的技术,允许我们将单个事件侦听器附加到单一元素,而该元素可以是大量其他元素的共同祖先。对于可以添加任意数量元素的用户生成内容,我们往往可以通过事件委托提高其执行效率。整个过程会用到事件冒泡,具体如下:

  1. 将事件侦听器附加至容器元素。

  2. 在事件处理程序中使用 event 参数,检查 event.target 属性以查看事件源。可以选择使用 event.target.closest(selector) API 来检查祖先元素。

  3. 如果该事件源就是我们所关注的元素或者其子元素,则进行处理。

 

更新后的代码如下所示:


 

  1. 我们修改了 initMediaViewer 方法,将一个点击事件侦听器附加到了包含所有图像的单一容器元素上。

  2. 在 onClickImage 方法中,我使用 ev.target.closest(selector) API 来检查点击是否来自缩略图元素或者其子元素。如果都不是,代码会提前返回,因为这里只需要关注对缩略图的点击。如果是,则代码将处理该事件。

 

总结


我们分别通过两轮部署,将步骤 1 和步骤 2 中的优化发布到了生产环境。

 

根据维基百科的综合性能测试数据,在 Moto G(5)实机测试当中,首轮部署将总阻塞时间缩短了约 200 毫秒,第二轮部署进一步缩短了约 80 毫秒。总体而言,这两个步骤让 Moto G(5)等移动设备访问长文章时的总阻塞时间缩短了约 300 毫秒。

 


 维基百科通过 Moto G(5)在综合性能测试中访问“瑞典”词条

 

虽然仍有进一步改进空间,且查询任务仍高于建议的低端设备延迟上限,但此次优化还是取得了显著成果。为了更大程度缩短总阻塞时间,后续可能有必要将任务拆分成更多小任务。

 

此次试验表明,有针对性的小规模优化有望实现显著的性能改进。通过删除或优化特定代码片段,看似微小的更改也会对网站的整体性能产生重大影响。换言之,要想在所有设备上改善响应速度和浏览体验,并不一定要对代码库开展复杂且广泛的修改。有时候,小小一点调整就足以引发性能质变。

 

原文链接:

https://www.nray.dev/blog/300ms-faster-reducing-wikipedias-total-blocking-time/

 

相关阅读:


维基百科技术架构

怎样搭建企业内部维基百科

如何自己搞一个维基百科?

spark 实战之:分析维基百科网站统计数据 (java 版)

活动推荐:

2023年9月3-5日,「QCon全球软件开发大会·北京站」 将在北京•富力万丽酒店举办。此次大会以「启航·AIGC软件工程变革」为主题,策划了大前端融合提效、大模型应用落地、面向 AI 的存储、AIGC 浪潮下的研发效能提升、LLMOps、异构算力、微服务架构治理、业务安全技术、构建未来软件的编程语言、FinOps 等近30个精彩专题。咨询购票可联系票务经理 18514549229(微信同手机号)。

2023-06-27 09:431821

评论

发布
暂无评论
发现更多内容

跑跑回收系统小程序开发

ALVIS

LeetCode题解:61. 旋转链表,双指针,JavaScript,详细注释

Lee Chen

算法 大前端 LeetCode

新工具上线!sdkmgr命令行助力流水线构建

科技汇

下一个颠覆的领域:区块链如何影响审计行业?(中)

CECBC

本夕生活小程序定制开发

ALVIS

医院预约管理系统开发

ALVIS

绿色篮子系统开发是什么模式?

ALVIS

正式发布!中国信通院联合腾讯安全等起草单位,共同发布研发运营安全工具系列标准

腾讯安全云鼎实验室

云计算 中国信通院 安全工具系列标准

行云管家荣获CFS第十届财经峰会2021科技创新引领奖!

行云管家

行云管家 财经峰会

咔嗒回收系统小程序开发

ALVIS

万能小哥系统开发是什么?

ALVIS

ISC网络安全大会关于“新型网络犯罪打击与治理”的分析

郑州埃文科技

网络安全 isc

微服务架构设计模式-进程间通信

以吻封笺

微服务 设计模式

解读区块链技术对量子攻击的脆弱性以及量子安全区块链的解决方案

CECBC

阿里云视频云发布实时高清VVC编码器Ali266,真正开启VVC商用之路

阿里云视频云

阿里云 视频编码 视频处理 编码器 视频云

家政公司管理系统开发介绍

ALVIS

完备的娱乐行业知识图谱库如何建成?爱奇艺知识图谱落地实践

爱奇艺技术产品团队

nlp 搜索 知识图谱

爱奇艺搜索排序算法实践(内附福利)

爱奇艺技术产品团队

排序算法 nlp 搜索

CloudQuery v1.4.1 发布 | 开放「组织架构」模块 API

BinTools图尔兹

数据库 数据安全 OpenAPI 数据库管控

SpringBoot自动配置原理解析

程序员阿杜

spring Boot Starter

互联网大厂一手资料,25大专题,500多页,背废你就能吊打面试官

Java架构师迁哥

好慷在家系统开发前景

ALVIS

主流分布式文件系统选型,写得太好了!

编程菌

Java 编程 程序员 计算机 技术宅

女巫面具系统模式开发

ALVIS

绿森林回收系统小程序开发

ALVIS

ElasticJob 3.0.0:打造面向互联网生态和海量任务的分布式调度解决方案

SphereEx

数据库 开源

绿地回收系统开发|现成小程序

ALVIS

希望体验更好的开发流程

escray

学习 极客时间 朱赟的技术管理课 7月日更

IDEA http client无法解析enviroment file

crazylle

IDEA http client Alibaba Cloud Toolkit

RocketMQ事物消息调研

crazylle

RocketMQ 事物消息

企业管云就用行云管家!省时省力省心!

行云管家

云计算 企业上云 行云管家 企业管云

  • 扫码添加小助手
    领取最新资料包
300毫秒分胜负:维基百科的总阻塞时间优化之道_大前端_InfoQ精选文章