async/await 是 Promise 的语法糖,底层基于 Promise 构建,async 函数自动返回 Promise,await 将后续代码作为微任务挂起并编译为 Promise.then 链。

async 与 await 并不是全新的异步机制,而是 Promise 的语法糖,底层完全基于 Promise 构建,不改变 JavaScript 的事件循环模型,也不引入新类型的异步原语。
async 函数的本质是自动包装的 Promise
声明一个 async 函数,等价于手动返回一个 Promise:
- 函数体执行结果(非 Promise)会被
Promise.resolve()包装; - 函数中抛出异常会自动转为
Promise.reject(); - 即使函数内部没有显式 return,也默认返回
Promise.resolve(undefined)。
例如:
async function foo() { return 42; }等价于:
function foo() { return Promise.resolve(42); }
await 的本质是 yield + Promise.then 的语法封装
await 并非暂停线程,而是在当前 Promise resolve 后,将后续代码作为微任务(microtask)挂起,交由 Promise 链调度:
立即学习“Java免费学习笔记(深入)”;
- 遇到
await expr时,引擎会立即执行expr(必须是 thenable 或 Promise),并暂停当前 async 函数的执行上下文; - 后续语句被编译进
Promise.then()回调中,形成隐式链式调用; - await 只能在 async 函数或模块顶层(ES2022+)中使用,因为需要依赖函数被编译为 Promise 驱动的状态机。
编译视角:V8 中的 async 函数被转为状态机
V8 引擎(及多数现代 JS 引擎)在解析 async 函数时,会将其重写为基于 Promise 和生成器风格的状态机:
- 每个 await 断点对应一个状态(state);
- 函数体被拆分为多个片段,用
Promise.then串联; - 错误处理(try/catch)被映射为
.catch()分支; - 整个过程无需 generator 函数或
function*,但逻辑结构与之高度相似。
不能脱离 Promise 理解 await
await 后接的表达式若非 Promise,会先被 Promise.resolve() 转换。这意味着:
-
await 123→ 立即进入下一个微任务(等价于Promise.resolve(123).then(...)); -
await null、await undefined同理; - 若误以为 await 能“等待任意值”,就可能忽略它实际触发的是 Promise 解析流程,而非时间等待。










