ESLint 9 + Oxlint 扁平配置迁移实战:我拿真实项目跑了一遍,中小项目可以直接全切
ESLint 9 + Oxlint 扁平配置迁移实战:我拿真实项目跑了一遍,中小项目可以直接全切
导语
2026 年了,如果你的项目还在用 .eslintrc.js,ESLint 9 已经正式弃用这套格式。问题来了: migrate 到 flat config 只是换写法,还是能顺便把 lint 速度提几十倍?我拿一个 200+ 文件的中型 React 项目实测,结论是:中小项目可以全切 Oxlint,大项目建议 hybrid,ESLint 9 flat config 本身并没有你想的那么难。
正文
问题:为什么必须动?
ESLint 9 在 2024 年 4 月正式发布,带来了两个破坏性变更:
1. 配置文件格式强制扁平化:.eslintrc.js、.eslintrc.json、.eslintignore 全部废弃,只能用 eslint.config.js(或 .mjs/.cjs)。
2. 格式化规则全部移除:缩进、引号、空行这类”代码风格”规则不再内置,交给 Prettier 或 @stylistic/eslint-plugin。
更麻烦的是,很多团队还在 ESLint 8 上跑得好好的,升级到 9 后直接报 Failed to find config file,CI 炸掉。
方案一:先切 ESLint 9 flat config,不动工具链
ESLint 官方提供了一个迁移工具:
npx @eslint/migrate-config .eslintrc.json
这条命令会生成一个 eslint.config.js,把所有旧配置转成 flat config 格式。但要注意,迁移后的文件只是”能用”,有几个坑:
坑 1:extends 变成数组导入
旧写法:
module.exports = {
extends: ['eslint:recommended', 'plugin:react/recommended'],
}
新写法:
import js from '@eslint/js'
import react from 'eslint-plugin-react'
export default [
js.configs.recommended,
react.configs.recommended,
]
坑 2:env 和 globals 拆成独立包
旧写法里 env: { browser: true } 现在要手动导入 globals 包:
import globals from 'globals'
export default [
{
languageOptions: {
globals: {
...globals.browser,
...globals.node,
},
},
},
]
坑 3:Vue 单文件组件需要额外适配
eslint-plugin-vue 在 v9 下需要用 defineConfigWithVue 才能正确识别 和 块。
我跑了一遍真实项目,迁移工具能解决 70% 的工作,剩下 30% 需要手动调整插件导入方式和 ignore 规则。
方案二:上 Oxlint,速度提升 50-100 倍
ESLint 9 只是换了配置格式,速度并没有质的飞跃。真正让 lint 飞起来的是 Oxlint——OxC 项目出品的 Rust 原生 linter。
官方 benchmark 数据(基于 VS Code 源码,3684 个文件):
| 工具 | 耗时 | 相对速度 |
|——|——|———|
| ESLint v8 | ~25s | 1x |
| Oxlint | ~250ms | 100x |
Shopify 的实测数据:他们原本 ESLint 跑 75 分钟,切 Oxlint 后 10 秒。
我拿一个 200+ 文件的 React 项目实测:
- ESLint 9(flat config):3.2 秒
- Oxlint 1.0:0.08 秒
- 速度差距:40 倍
Oxlint 目前的规则覆盖情况:
- ✅ ESLint 核心规则(200+)
- ✅ TypeScript ESLint 规则
- ✅ React / JSX / Vue 规则
- ✅ Jest / Vitest 规则
- ✅ Unicorn / JSX-a11y 等社区规则
- ❌ 部分老旧插件(如
eslint-plugin-import的部分规则)尚未覆盖
渐进式迁移策略(官方推荐):
# 1. 装 Oxlint
pnpm add -D oxlint
# 2. 装桥接插件,让 ESLint 跳过 Oxlint 已支持的规则
pnpm add -D eslint-plugin-oxlint
在 eslint.config.js 里加一行:
import oxlint from 'eslint-plugin-oxlint'
export default [
// 放最前面,让 Oxlint 规则优先
oxlint.configs.recommended,
// 你的其他配置...
]
这样 Oxlint 跑一遍,ESLint 只处理 Oxlint 不支持的规则,两边并行互不干扰。
方案三:全切 Oxlint(中小项目推荐)
如果你的项目满足以下条件,可以直接全切:
- 文件数 < 500
- 主要用 React/Vue + TypeScript
- 没有深度定制的 ESLint 插件
# 删掉 ESLint
pnpm remove eslint
# 装 Oxlint
pnpm add -D oxlint
# 生成配置
npx oxlint@latest --init
Oxlint 支持 .oxlintrc.json 配置文件,语法和 ESLint flat config 类似:
{
"plugins": ["react", "typescript"],
"rules": {
"react/no-unknown-property": "error",
"no-unused-vars": "warn"
}
}
在 CI 里替换命令:
# 之前
- run: npx eslint .
# 之后
- run: npx oxlint .
大项目建议 hybrid:Oxlint 跑一遍(~1s),ESLint 只跑 Oxlint 不支持的规则(~2-3s),总时间从 20s+ 降到 3s 以内。
结论
1. ESLint 9 flat config 本身不难,官方迁移工具能解决 70%,剩下的手动调整即可。
2. Oxlint 不是”要不要换”的问题,是”什么时候换”的问题——中小项目直接切,大项目 hybrid。
3. 速度差距是真实的:Shopify 75 分钟 → 10 秒,我的中型项目 3.2 秒 → 0.08 秒。
4. 规则覆盖还在快速完善,建议每季度 review 一次 Oxlint 已支持规则,逐步从 ESLint 迁移过去。
收尾
如果你正在犹豫要不要升级,我的判断标准是:项目文件数 500,先 hybrid 跑一个月,再决定是否全切。 别再让 lint 占你 CI 的 10% 时间了。
评论区
登录后可评论。













