跳至内容

ESLint

Next.js 开箱即用地提供了集成的 ESLint 体验。将 next lint 作为脚本添加到 package.json

package.json
{
  "scripts": {
    "lint": "next lint"
  }
}

然后运行 npm run lintyarn lint

终端
yarn lint

如果你的应用中尚未配置 ESLint,系统将引导你完成安装和配置过程。

终端
yarn lint

你将看到类似这样的提示

? 你希望如何配置 ESLint?

❯ 严格模式 (推荐)
基础模式
取消

可以选择以下三个选项之一

  • **严格模式**:包含 Next.js 的基础 ESLint 配置以及更严格的 核心 Web 指标规则集。对于首次为开发者设置 ESLint 的用户,此配置是推荐的配置。

    .eslintrc.json
    {
      "extends": "next/core-web-vitals"
    }
  • **基础模式**:包含 Next.js 的基础 ESLint 配置。

    .eslintrc.json
    {
      "extends": "next"
    }
  • **取消**:不包含任何 ESLint 配置。仅当你计划设置自己的自定义 ESLint 配置时,才选择此选项。

如果选择了这两个配置选项之一,Next.js 将自动将 eslinteslint-config-next 作为依赖项安装到你的应用中,并在项目的根目录中创建一个包含你所选配置的 .eslintrc.json 文件。

现在,你可以随时运行 next lint 来运行 ESLint 以捕获错误。ESLint 设置完成后,它还将在每次构建 (next build) 期间自动运行。错误将导致构建失败,而警告则不会。

如果你不希望 ESLint 在 next build 期间运行,请参阅 忽略 ESLint 的文档。

我们建议使用合适的 集成,以便在开发过程中直接在你的代码编辑器中查看警告和错误。

ESLint 配置

默认配置 (eslint-config-next) 包含你在 Next.js 中获得最佳开箱即用代码风格检查体验所需的一切。如果你的应用中尚未配置 ESLint,我们建议使用 next lint 来设置 ESLint 以及此配置。

如果你想将 eslint-config-next 与其他 ESLint 配置一起使用,请参阅 其他配置 部分,了解如何在不引起任何冲突的情况下执行此操作。

以下 ESLint 插件中的推荐规则集都用于 eslint-config-next

这将优先于 next.config.js 中的配置。

ESLint 插件

Next.js 提供了一个 ESLint 插件,eslint-plugin-next,它已包含在基础配置中,可以帮助您捕获 Next.js 应用程序中的常见问题。完整的规则集如下所示。

在推荐的配置中启用

规则描述
@next/next/google-font-display强制使用 Google Fonts 的字体显示行为。
@next/next/google-font-preconnect确保与 Google Fonts 一起使用 preconnect
@next/next/inline-script-id强制在具有内联内容的 next/script 组件上使用 id 属性。
@next/next/next-script-for-ga在使用 Google Analytics 的内联脚本时,优先使用 next/script 组件。
@next/next/no-assign-module-variable防止给 module 变量赋值。
@next/next/no-async-client-component防止客户端组件为异步函数。
@next/next/no-before-interactive-script-outside-document防止在 pages/_document.js 之外使用 next/scriptbeforeInteractive 策略。
@next/next/no-css-tags防止手动添加样式表标签。
@next/next/no-document-import-in-page防止在 pages/_document.js 之外导入 next/document
@next/next/no-duplicate-head防止在 pages/_document.js 中重复使用 <Head>
@next/next/no-head-element防止使用 <head> 元素。
@next/next/no-head-import-in-document防止在 pages/_document.js 中使用 next/head
@next/next/no-html-link-for-pages防止使用 <a> 元素导航到内部 Next.js 页面。
@next/next/no-img-element由于 LCP 较慢且带宽较高,因此防止使用 <img> 元素。
@next/next/no-page-custom-font防止仅页面自定义字体。
@next/next/no-script-component-in-head防止在 next/head 组件中使用 next/script
@next/next/no-styled-jsx-in-document防止在 pages/_document.js 中使用 styled-jsx
@next/next/no-sync-scripts防止同步脚本。
@next/next/no-title-in-document-head防止使用来自 next/documentHead 组件中的 <title>
@next/next/no-typos防止 Next.js 的数据获取函数 中的常见拼写错误。
@next/next/no-unwanted-polyfillio防止来自 Polyfill.io 的重复 polyfill。

如果您已经在应用程序中配置了 ESLint,我们建议直接从该插件扩展,而不是包含 eslint-config-next(除非满足几个条件)。请参阅 推荐的插件规则集 以了解更多信息。

自定义设置

rootDir

如果您在 Next.js 未安装在根目录(例如单一仓库)的项目中使用 eslint-plugin-next,则可以使用 .eslintrc 中的 settings 属性告诉 eslint-plugin-next 在哪里找到您的 Next.js 应用程序。

.eslintrc.json
{
  "extends": "next",
  "settings": {
    "next": {
      "rootDir": "packages/my-app/"
    }
  }
}

rootDir 可以是路径(相对或绝对),glob(例如 "packages/*/")或路径和/或 glob 的数组。

棉绒自定义目录和文件

默认情况下,Next.js 将为 pages/app/components/lib/src/ 目录中的所有文件运行 ESLint。但是,您可以使用 next.config.jseslint 配置的 dirs 选项为生产构建指定要检查的目录。

next.config.js
module.exports = {
  eslint: {
    dirs: ['pages', 'utils'], // Only run ESLint on the 'pages' and 'utils' directories during production builds (next build)
  },
}

类似地,--dir--file 标志可用于 next lint 以检查特定目录和文件。

终端
next lint --dir pages --dir utils --file bar.js

缓存

为了提高性能,默认情况下会缓存 ESLint 处理的文件信息。这些信息存储在 .next/cache 或您定义的 构建目录 中。如果您包含任何依赖于单个源文件以外内容的 ESLint 规则,并且需要禁用缓存,请在 next lint 中使用 --no-cache 标志。

终端
next lint --no-cache

禁用规则

如果您想修改或禁用支持的插件(reactreact-hooksnext)提供的任何规则,您可以使用 .eslintrc 中的 rules 属性直接更改它们。

.eslintrc.json
{
  "extends": "next",
  "rules": {
    "react/no-unescaped-entities": "off",
    "@next/next/no-page-custom-font": "off"
  }
}

核心 Web 指标

首次运行 next lint 并选择 严格 选项时,将启用 next/core-web-vitals 规则集。

.eslintrc.json
{
  "extends": "next/core-web-vitals"
}

next/core-web-vitals 会更新 eslint-plugin-next,如果某些规则会影响 核心 Web 指标,则会将其从默认的警告改为错误。

使用 Create Next App 构建的新应用程序会自动包含 next/core-web-vitals 入口点。

TypeScript

除了 Next.js ESLint 规则外,create-next-app --typescript 还会将 TypeScript 特定的 lint 规则与 next/typescript 一起添加到您的配置中。

.eslintrc.json
{
  "extends": ["next/core-web-vitals", "next/typescript"]
}

这些规则基于 plugin:@typescript-eslint/recommended。有关更多详细信息,请参阅 typescript-eslint > Configs

与其他工具一起使用

Prettier

ESLint 还包含代码格式化规则,这可能会与您现有的 Prettier 设置冲突。我们建议在您的 ESLint 配置中包含 eslint-config-prettier,以使 ESLint 和 Prettier 协同工作。

首先,安装依赖项。

终端
npm install --save-dev eslint-config-prettier
 
yarn add --dev eslint-config-prettier
 
pnpm add --save-dev eslint-config-prettier
 
bun add --dev eslint-config-prettier

然后,将 prettier 添加到您现有的 ESLint 配置中。

.eslintrc.json
{
  "extends": ["next", "prettier"]
}

lint-staged

如果您想将next lintlint-staged结合使用,以便在暂存的 Git 文件上运行代码检查器,则需要在项目的根目录下的.lintstagedrc.js文件中添加以下内容,以指定--file标志的使用。

.lintstagedrc.js
const path = require('path')
 
const buildEslintCommand = (filenames) =>
  `next lint --fix --file ${filenames
    .map((f) => path.relative(process.cwd(), f))
    .join(' --file ')}`
 
module.exports = {
  '*.{js,jsx,ts,tsx}': [buildEslintCommand],
}

迁移现有配置

如果您已经在应用程序中配置了 ESLint,并且以下任一条件成立

  • 您已经安装了一个或多个以下插件(单独安装或通过其他配置,如airbnbreact-app安装)
    • react
    • react-hooks
    • jsx-a11y
    • import
  • 您定义的特定parserOptions与 Next.js 中 Babel 的配置不同(除非您自定义了 Babel 配置,否则不建议这样做)
  • 您已安装eslint-plugin-import,并使用 Node.js 和/或 TypeScript 定义了解析器来处理导入

那么我们建议您,如果您更喜欢在eslint-config-next中配置这些属性的方式,则可以移除这些设置;或者直接从 Next.js ESLint 插件扩展

module.exports = {
  extends: [
    //...
    'plugin:@next/next/recommended',
  ],
}

该插件可以在您的项目中正常安装,无需运行next lint

终端
npm install --save-dev @next/eslint-plugin-next
 
yarn add --dev @next/eslint-plugin-next
 
pnpm add --save-dev @next/eslint-plugin-next
 
bun add --dev @next/eslint-plugin-next

这消除了由于在多个配置中导入相同的插件或解析器而可能发生的冲突或错误的风险。

其他配置

如果您已经使用单独的 ESLint 配置,并且想要包含eslint-config-next,请确保在其他配置之后最后扩展它。例如

.eslintrc.json
{
  "extends": ["eslint:recommended", "next"]
}

next配置已经处理了为parserpluginssettings属性设置默认值。除非您需要针对您的用例进行不同的配置,否则无需手动重新声明任何这些属性。

如果您包含任何其他可共享的配置,**您需要确保这些属性不会被覆盖或修改**。否则,我们建议移除任何与next配置共享行为的配置,或者如上所述,直接从 Next.js ESLint 插件扩展。