该用 preload 而非 prefetch 的情形是:当前页面渲染或交互立刻需要的资源,如 main.css、iconfont.woff2、hero-image.webp;它不是提前下载,而是“现在就要且默认加载太晚”,错用会抢带宽拖慢 LCP。

什么时候该用 preload,而不是 prefetch
只有当前页面渲染或交互**立刻需要**的资源,才适合 preload。它不是“提前下载”,而是“现在就要,且默认加载太晚”。
常见误用:把路由懒加载的 next-page.js 写成 preload —— 它根本不会在当前页执行,却抢了 CSS 和字体的带宽,直接拖慢 LCP。
-
preload适用场景:main.css(关键样式)、iconfont.woff2(首屏字体)、hero-image.webp(<img>的srcset中确定会用的那张图) - 不适用:
user-profile.js(跳转后才用)、analytics.js(异步非关键)、print.css(媒体查询未匹配) - 验证是否合理:Chrome DevTools → Network → 刷新 → 找到该资源 → 看
Priority列是不是Highest或High;如果不是,大概率是as错了或路径 404
preload 必须带 as,但 prefetch 可以不带
as 不是可选项,是浏览器调度资源优先级和缓存复用的依据。漏写或写错,preload 就失效——它会被当成普通 fetch,优先级掉到最低,甚至触发二次请求。
比如字体没加 crossorigin,浏览器发了请求,但响应被丢弃(无报错),FOIT 持续,而带宽已被占用。
立即学习“前端免费学习笔记(深入)”;
-
as="style"→ 触发最高优先级,匹配<link rel="stylesheet">的 Accept 头 -
as="font"→ 强制要求crossorigin,否则跨域字体白加载 -
as="script"→ 优先级低于style,但高于image;若脚本已用defer或type="module",再preload就冗余 -
prefetch虽不强制as,但建议加上(如as="script"),否则浏览器仅靠 MIME 类型推断,可能降级处理或缓存策略不准
prefetch 不保证执行,且资源不能跨源复用
prefetch 是低优先级后台任务,浏览器只在 window.onload 后、CPU 空闲、网络未拥塞、没开省流模式时才发起。它不参与当前渲染流水线,但一旦触发,仍是完整 HTTP 请求。
很多人以为 prefetch 的资源能被 preload 缓存复用,其实不能:preload 进的是「当前页面专用缓存分区」,prefetch 进的是常规 HTTP 缓存,两者隔离。
- 跨域
prefetch在部分浏览器中被忽略(如 Safari 对跨域 JS prefetch 支持有限) - 如果
prefetch的资源没配Cache-Control: public, max-age=31536000,下次跳转仍要重下,预取完全失效 - 首页 banner 图设成
rel="prefetch"?浏览器真等到所有 JS/CSS 加完才拉,LCP 直接拖慢 300ms+
同页面同时存在 preload 和 prefetch,它们不直接抢带宽
它们不在同一调度队列里竞争:preload 进「高优渲染队列」,prefetch 进「后台空闲队列」。真正的问题从来不是它们互抢,而是 preload 用错了对象。
比如把商品详情页的 product-detail.js 错标为 preload,它就会和首页的 main.css 争 Highest 优先级,导致关键样式延迟解析——这不是浏览器 bug,是你把“未来需求”当成了“现在刚需”。
-
preload错用 = 当前页性能受损 -
prefetch错用 = 带宽浪费 + 缓存污染 - 构建工具(如 Vite 插件)可自动注入
prefetch,但必须基于真实路由跳转概率;preload几乎必须手写,且需逐个验证是否被实际使用(控制台警告 “resource preloaded but not used” 是明确信号)



















