断网时页面必须立刻显示静态内容,所有首屏文本须写死在初始html的内,禁用js注入、及data-*占位;关键样式内联且精简(≤14kb gzip),禁用@import和阻塞字体策略,dom结构扁平化,确保流式解析不中断。

断网时页面必须能立刻显示静态内容,不能等 JS 加载
弱网或离线状态下,DOMContentLoaded 通常要等几秒才触发,但用户需要的是“打开就有字”。这意味着所有首屏文本必须写死在初始 HTML 的 <main></main> 里,不包裹、不延迟、不依赖 JS 注入。
- 标题、副标题、核心说明文字直接写在
<main></main>开头,例如:<main><h1 lang="zh-CN">服务暂时不可用</h1> <p>请检查网络连接后重试</p></main> - 禁用
<template></template>、<script type="text/template"></script>或data-content占位——这些在 JS 未执行前就是空节点 -
<noscript></noscript>不是降级容器:它只在 JS 被浏览器彻底禁用时生效,且不会替换已有 DOM;把它当 fallback 模板塞进 JS 启用的页面里,根本不会被解析
关键样式必须内联,且只保留影响文本渲染的最小集合
哪怕 HTML 里写了文字,如果 CSS 文件还没加载完,浏览器可能卡住不绘制——弱网下这个等待常达 2–3 秒。解决方案不是删掉样式,而是切分并内联真正关键的部分。
- 只把
body字体、h1/p行高/颜色/边距等直接影响首屏文本排版的规则放进<style></style>,体积控制在 ≤14KB(gzip 后约 4–8KB) - 禁用
@import:它会让 CSS 加载串行化,3G 下可能多拖 800ms - 所有动画关键帧(
@keyframes)、复杂媒体查询(如@media (prefers-reduced-motion))必须从关键 CSS 中剥离,延迟加载 - 字体策略统一用
font-display: swap;block会导致文本长时间不可见,optional可能直接不加载
DOM 结构要扁平,避免嵌套过深阻塞解析
浏览器是流式解析 HTML 的,每层嵌套都会增加 token 解析和节点创建开销。弱网下 HTML 下载慢,解析阶段 CPU 压力反而更明显——尤其低端安卓机上,6 层嵌套的 <div> 可能让首屏文本延迟 200ms+ 出现。
<ul>
<li>
<code><main></main> 内部只保留 LCP 元素所需最小 DOM:标题、主图(带 loading="eager")、核心按钮
<div data-lazy="comments"></div>,不带子节点、不设 innerHTML
div > div > div > article)优先用 display: contents 扁平化(注意 Safari 15.4+ 才支持)<div></div> 和无 class/id 的冗余 wrapper——它们仍参与 DOM 构建,白占内存和解析时间JS 容灾不能只靠 onerror,必须主动超时中断
弱网下 fetch 请求常卡在 pending 状态,既不触发 onerror 也不返回响应头。等它自然失败,用户已看到几秒白屏。必须用 AbortController 主动干预。
- 关键 JS(如路由入口、渲染器)fetch 超时阈值设为
1500ms,不是凭感觉;实测中 >800ms 延迟已显著拖慢 FCP - 每次 fetch 都新建
AbortController实例,复用会导致abort()失效 - 中断后立即注入轻量 fallback 脚本(如只挂载静态 DOM 或显示 skeleton),而非尝试重试
- 离线包加载失败后,先检查
navigator.onLine;若为false,直接启用内联 fallback 数据(如预置 JSON 或空数组)
最容易被忽略的点是:文本是否真正在初始 HTML 里、是否带 lang 属性、是否被无意义 wrapper 包裹——这些细节决定用户第一眼看到的是文字,还是空白。











