Turbopack
Turbopack 是一个增量打包器,专为 JavaScript 和 TypeScript 优化,用 Rust 编写,并内置于 Next.js 中。您可以将 Turbopack 与 Pages 和 App Router 配合使用,以获得更快的本地开发体验。
为何选择 Turbopack?
我们构建 Turbopack 是为了提升 Next.js 的性能,其中包括
- 统一图: Next.js 支持多种输出环境(例如,客户端和服务器)。管理多个编译器并将包缝合在一起可能很繁琐。Turbopack 为所有环境使用单个统一图。
- 打包与原生 ESM: 有些工具在开发中跳过打包,并依赖浏览器的原生 ESM。这对于小型应用程序很有效,但由于过多的网络请求,可能会减慢大型应用程序的速度。Turbopack 在开发中打包,但以优化方式保持大型应用程序的快速。
- 增量计算: Turbopack 在多个核心之间并行工作,并将结果缓存到函数级别。一旦完成一项工作,Turbopack 不会重复它。
- 懒惰打包: Turbopack 只打包开发服务器实际请求的内容。这种懒惰方法可以减少初始编译时间和内存使用。
开始使用
Turbopack 现在是 Next.js 中的默认打包器。使用 Turbopack 无需配置
{
"scripts": {
"dev": "next dev",
"build": "next build",
"start": "next start"
}
}使用 Webpack 而不是 Turbopack
如果需要使用 Webpack 而不是 Turbopack,可以使用 --webpack 标志进行选择
{
"scripts": {
"dev": "next dev --webpack",
"build": "next build --webpack",
"start": "next start"
}
}支持的功能
Next.js 中的 Turbopack 对于常见用例是零配置的。以下是开箱即用支持的功能摘要,以及在需要时如何进一步配置 Turbopack 的一些参考。
语言功能
| 功能 | 状态 | 备注 |
|---|---|---|
| JavaScript 和 TypeScript | 支持 | 底层使用 SWC。类型检查不由 Turbopack 完成(运行 tsc --watch 或依赖您的 IDE 进行类型检查)。 |
| ECMAScript (ESNext) | 支持 | Turbopack 支持最新的 ECMAScript 功能,与 SWC 的覆盖范围一致。 |
| CommonJS | 支持 | require() 语法开箱即用。 |
| ESM | 支持 | 静态和动态 import 完全支持。 |
| Babel | 支持 | 从 Next.js 16 开始,如果 Turbopack 检测到配置文件,它会自动使用 Babel。与 webpack 不同,SWC 始终用于 Next.js 的内部转换和降级到旧版 ECMAScript。如果存在 Babel 配置文件,带 webpack 的 Next.js 将禁用 SWC。node_modules 中的文件被排除,除非您手动配置 babel-loader。 |
框架和 React 功能
| 功能 | 状态 | 备注 |
|---|---|---|
| JSX / TSX | 支持 | SWC 处理 JSX/TSX 编译。 |
| 快速刷新 | 支持 | 无需配置。 |
| React Server Components (RSC) | 支持 | 适用于 Next.js App Router。Turbopack 确保正确的服务器/客户端打包。 |
| 根布局创建 | 不支持 | App Router 中不支持自动创建根布局。Turbopack 将指导您手动创建。 |
CSS 和样式
| 功能 | 状态 | 备注 |
|---|---|---|
| 全局 CSS | 支持 | 直接在应用程序中导入 .css 文件。 |
| CSS 模块 | 支持 | .module.css 文件原生支持(Lightning CSS)。 |
| CSS 嵌套 | 支持 | Lightning CSS 支持现代 CSS 嵌套。 |
| @import 语法 | 支持 | 组合多个 CSS 文件。 |
| PostCSS | 支持 | 自动在 Node.js 工作池中处理 postcss.config.js。适用于 Tailwind、Autoprefixer 等。 |
| Sass / SCSS | 支持 (Next.js) | 对于 Next.js,Sass 开箱即用。不支持自定义 Sass 函数 (sassOptions.functions),因为 Turbopack 基于 Rust 的架构无法直接执行 JavaScript 函数,这与 webpack 的 Node.js 环境不同。如果需要此功能,请使用 webpack。将来,Turbopack 独立使用可能需要加载器配置。 |
| Less | 计划通过插件实现 | 默认尚不支持。一旦自定义加载器稳定,可能需要加载器配置。 |
| Lightning CSS | 正在使用中 | 处理 CSS 转换。一些低使用率的 CSS Modules 功能(如 :local/:global 作为独立伪类)尚不支持。有关详细信息,请参阅下文。 |
资产
| 功能 | 状态 | 备注 |
|---|---|---|
| 静态资产(图片、字体) | 支持 | import img from './img.png' 开箱即用。在 Next.js 中,返回一个用于 <Image /> 组件的对象。 |
| JSON 导入 | 支持 | 支持从 .json 文件进行命名或默认导入。 |
模块解析
| 功能 | 状态 | 备注 |
|---|---|---|
| 路径别名 | 支持 | 读取 tsconfig.json 的 paths 和 baseUrl,与 Next.js 行为一致。 |
| 手动别名 | 支持 | 在 next.config.js 中配置 resolveAlias(类似于 webpack.resolve.alias)。 |
| 自定义扩展名 | 支持 | 在 next.config.js 中配置 resolveExtensions. |
| AMD | 部分支持 | 基本转换有效;高级 AMD 用法有限。 |
性能和快速刷新
| 功能 | 状态 | 备注 |
|---|---|---|
| 快速刷新 | 支持 | 更新 JavaScript、TypeScript 和 CSS,无需完全刷新。 |
| 增量打包 | 支持 | Turbopack 懒惰地构建开发服务器请求的内容,加速大型应用程序。 |
与 webpack 的已知差距
在迁移应用程序时,webpack 和 Turbopack 之间存在许多重要的行为差异,需要注意。通常,这些对于新应用程序来说不是问题。
CSS 模块排序
Turbopack 将遵循 JS 导入顺序来排序未指定顺序的CSS 模块。例如
import utilStyles from './utils.module.css'
import buttonStyles from './button.module.css'
export default function BlogPost() {
return (
<div className={utilStyles.container}>
<button className={buttonStyles.primary}>Click me</button>
</div>
)
}在此示例中,Turbopack 将确保 utils.module.css 将在生成的 CSS 块中出现在 button.module.css 之前,遵循导入顺序
Webpack 通常也会这样做,但在某些情况下它会忽略 JS 推断的顺序,例如它推断 JS 文件是无副作用的。
如果应用程序依赖任意排序,这可能会在采用 Turbopack 时导致细微的渲染变化。通常,解决方案很简单,例如让 button.module.css @import utils.module.css 以强制排序,或者识别冲突的规则并更改它们以不针对相同的属性。
Sass node_modules 导入
Turbopack 开箱即用支持导入 node_modules Sass 文件。Webpack 支持旧版波浪号 ~ 语法,Turbopack 不支持。
从
@import '~bootstrap/dist/css/bootstrap.min.css';到
@import 'bootstrap/dist/css/bootstrap.min.css';如果无法更新导入,可以添加 turbopack.resolveAlias 配置将 ~ 语法映射到实际路径
module.exports = {
turbopack: {
resolveAlias: {
'~*': '*',
},
},
}包大小
根据我们对生产应用程序的测试,我们观察到 Turbopack 生成的包大小通常与 Webpack 相似。然而,比较可能很困难,因为 turbopack 倾向于生成更少但更大的块。我们的建议是关注更高层次的指标,例如核心 Web 生命体征或您自己的应用程序级指标来比较两种打包器的性能。然而,我们确实意识到一个可能偶尔导致大规模回归的差距。
Turbopack 尚未拥有 webpack 中默认启用的内部图优化的等效功能。此优化对于摇树大型模块很有用。例如
import heavy from 'some-heavy-dependency.js'
export function usesHeavy() {
return heavy.run()
}
export const CONSTANT_VALUE = 3如果应用程序只使用 CONSTANT_VALUE,Turbopack 将检测到这一点并删除 usesHeavy 导出,但不会删除相应的 import。然而,通过内部图优化,webpack 也可以删除 import,这也可以删除依赖项。
我们计划在 Turbopack 中提供等效的内部图优化,但仍在开发中。如果您受到此差距的影响,请考虑手动拆分模块。
构建缓存
Webpack 支持磁盘构建缓存以提高构建性能。Turbopack 提供了类似的选择加入功能,目前处于测试阶段。从 Next 16 开始,您可以通过设置以下实验性标志来启用 Turbopack 的文件系统缓存
须知: 因此,在比较 webpack 和 Turbopack 性能时,请务必在构建之间删除
.next文件夹以进行公平比较,或启用 turbopack 文件系统缓存功能。
Webpack 插件
Turbopack 不支持 webpack 插件。这会影响依赖 webpack 插件系统进行集成的第三方工具。我们确实支持webpack 加载器。如果您依赖 webpack 插件,则需要找到兼容 Turbopack 的替代方案,或者继续使用 webpack,直到提供等效功能。
不支持和未计划的功能
某些功能尚未实现或未计划
- 旧版 CSS Modules 功能
- 独立的
:local和:global伪类(仅支持函数变体:global(...))。 @value规则(已被 CSS 变量取代)。:import和:exportICSS 规则。.module.css中的composes组合.css文件。在 webpack 中,这将把.css文件视为 CSS 模块,而对于 Turbopack,.css文件将始终是全局的。这意味着如果要在 CSS 模块中使用composes,需要将.css文件更改为.module.css文件。- CSS Modules 中的
@import导入.css作为 CSS 模块。在 webpack 中,这将把.css文件视为 CSS 模块,而对于 Turbopack,.css文件将始终是全局的。这意味着如果要在 CSS 模块中使用@import,需要将.css文件更改为.module.css文件。
- 独立的
sassOptions.functions不支持在sassOptions.functions中定义的自定义 Sass 函数。此功能允许定义可在编译期间从 Sass 代码调用的 JavaScript 函数。Turbopack 基于 Rust 的架构无法直接执行通过sassOptions.functions传递的 JavaScript 函数,这与完全在 JavaScript 中运行的 webpack 基于 Node.js 的 sass-loader 不同。如果您正在使用自定义 Sass 函数,则需要使用 webpack 而不是 Turbopack。webpack()配置 在next.config.js中 Turbopack 取代了 webpack,因此不识别webpack()配置。请改用turbopack配置。- Yarn PnP 不计划在 Next.js 中支持 Turbopack。
experimental.urlImports不计划用于 Turbopack。experimental.esmExternals不计划。Turbopack 不支持 Next.js 中的旧版esmExternals配置。- 一些 Next.js 实验性标志
experimental.nextScriptWorkersexperimental.sri.algorithmexperimental.fallbackNodePolyfills我们计划将来实现这些功能。
有关每个功能标志及其状态的完整详细分类,请参阅Turbopack API 参考。
配置
Turbopack 可以通过 next.config.js(或 next.config.ts)在 turbopack 键下进行配置。配置选项包括
rules定义用于文件转换的额外webpack 加载器。resolveAlias创建手动别名(类似于 webpack 中的resolve.alias)。resolveExtensions更改或扩展模块解析的文件扩展名。
module.exports = {
turbopack: {
// Example: adding an alias and custom file extension
resolveAlias: {
underscore: 'lodash',
},
resolveExtensions: ['.mdx', '.tsx', '.ts', '.jsx', '.js', '.json'],
},
}有关更深入的配置示例,请参阅Turbopack 配置文档。
生成跟踪文件以进行性能调试
如果您遇到性能或内存问题并希望帮助 Next.js 团队诊断它们,可以通过在开发命令后附加 NEXT_TURBOPACK_TRACING=1 来生成跟踪文件
NEXT_TURBOPACK_TRACING=1 next dev这将生成一个 .next/dev/trace-turbopack 文件。在 Next.js 存储库上创建 GitHub issue 时,请包含此文件,以帮助我们进行调查。
默认情况下,开发服务器输出到 .next/dev。阅读有关isolatedDevBuild的更多信息。
总结
Turbopack 是一个基于 Rust 的增量打包器,旨在使本地开发和构建变得快速——特别是对于大型应用程序。它集成到 Next.js 中,提供零配置的 CSS、React 和 TypeScript 支持。
版本变更
| 版本 | 更改 |
|---|---|
v16.0.0 | Turbopack 成为 Next.js 的默认打包器。当找到配置文件时,自动支持 Babel。 |
v15.5.0 | Turbopack 支持 build 测试版 |
v15.3.0 | 对 build 的实验性支持 |
v15.0.0 | 用于 dev 的 Turbopack 稳定版 |
这有帮助吗?