顶级 await 仅限 ES 模块顶层使用,需满足三前提:文件为 ESM(.mjs 或 "type": "module")、HTML 中 script 标记 type="module"、运行环境支持(Node.js 14.8+ 或现代浏览器 ≥Chrome 89)。

顶级 await(Top-level await)只能在 ES 模块(ESM)的顶层作用域中直接使用,不能出现在普通脚本、CommonJS 文件或函数内部——它不是“任意地方都能写 await”,而是模块系统对初始化阶段的异步支持。
必须满足的运行环境条件
要让顶级 await 生效,三个前提缺一不可:
- 文件必须是 ES 模块:后缀为 .mjs,或在 package.json 中声明
"type": "module" - HTML 中引用时需显式标记:
<script type="module" src="main.mjs"></script>;仅写<script src="main.mjs"></script>会报错 - 运行环境需支持:Node.js 14.8+(v14.8 起需加
--experimental-top-level-await,v16+ 默认开启),现代浏览器(Chrome/Edge/Firefox ≥89,Safari ≥15.4)
典型用法示例
在模块顶层直接等待异步操作完成,并导出结果:
// config.mjs
const res = await fetch('/api/config.json');
if (!res.ok) throw new Error(`Config load failed: ${res.status}`);
const config = await res.json();
export { config };
其他模块导入时会自动等待该模块执行完毕:
// app.mjs
import { config } from './config.mjs';
console.log('Config ready:', config); // 这行一定在 fetch 完成后才执行
常见适用场景
适合做模块级一次性初始化任务,例如:
- 远程配置加载(如环境变量、功能开关)
- 动态选择并预加载依赖模块:
const envModule = await import(`./env-${process.env.NODE_ENV}.mjs`); - 建立初始数据库连接、认证令牌刷新、资源预取等启动前准备
需要注意的关键限制
顶级 await 不是语法糖,它改变了模块加载语义:
- 含顶级 await 的模块会变成“异步模块”,所有
import它的模块也会被阻塞,直到其 await 完成 - 不能用于条件分支或循环体内(如
if (...) await fetch(...)),必须写在模块最外层 - 错误未捕获会导致整个模块加载失败,表现为白屏或控制台报错后脚本中断,建议用
try/catch包裹关键 await - 不支持 CommonJS(
.cjs)、内联非模块 script、或通过require()加载的上下文


















