defer async preload prefetch modulepreload 的区别和应用场景,在 js 中下载和执行的优先级对比
script 加载属性与资源预加载指令对比
加载和执行特性对比表
特性 | 下载时机 | 执行时机 | 阻塞解析 | 执行顺序 | 优先级 | 适用场景 |
---|---|---|---|---|---|---|
普通 script | 立即下载 | 立即执行 | 阻塞 HTML 解析 | 按出现顺序 | 高 | 必须立即执行的核心脚本 |
defer | HTML 解析过程中下载 | DOM 构建完成后,DOMContentLoaded 事件前执行 | 不阻塞 | 按出现顺序执行 | 中 | 依赖 DOM 结构但不紧急的脚本 |
async | HTML 解析过程中下载 | 下载完成后立即执行 | 执行时阻塞 | 不保证顺序 | 中高 | 独立功能,不依赖其他脚本的场景 |
preload | 提前高优先级下载 | 不自动执行 | 不阻塞 | 不适用 | 高 | 当前页面必需资源(字体、样式、关键JS) |
prefetch | 空闲时低优先级下载 | 不自动执行 | 不阻塞 | 不适用 | 最低 | 未来页面可能需要的资源 |
modulepreload | 提前下载并解析 | 不自动执行 | 不阻塞 | 不适用 | 高 | ES模块及其依赖的预加载 |
详细说明
脚本加载属性
- defer:
<script defer src="script.js"></script>
- 适合有依赖关系且需要按顺序执行的脚本
- 确保在DOM就绪时执行,适合操作DOM的脚本
- async:
<script async src="script.js"></script>
- 适合第三方统计、广告脚本等独立功能
- 不适合有依赖关系的脚本
资源预加载指令
- preload:
<link rel="preload" href="style.css" as="style">
- 当前页面必定需要的资源,提高首屏加载性能
- 支持指定资源类型(as属性)和媒体查询
- prefetch:
<link rel="prefetch" href="next-page.js">
- 下一页可能用到的资源,浏览器空闲时加载
- 适合预加载分页内容、可能跳转的页面资源
- modulepreload:
<link rel="modulepreload" href="module.js">
- 专为ES模块设计,可同时预加载依赖模块
- 比普通preload更高效,减少级联请求