Next.jsによるWebアプリケーション開発概論

Next.jsとESLintの初期設定

この節で学ぶこと

この節では、ESLint が何をする道具なのか、Next.js で最初にどう設定するのか、そして 「どこまで厳しくするか」 の考え方を学びます。

ESLint 公式は、ESLint を「ECMAScript/JavaScript コード内のパターンを識別して報告し、コードを一貫させ、バグを避けることを目的としたツール」と説明しています。

Next.js は eslint-config-next を提供しており、@next/eslint-plugin-next に加えて eslint-plugin-reacteslint-plugin-react-hooks の推奨ルール群を含みます。

初心者にとって ESLint は、最初は「怒られる仕組み」に見えがちです。けれど実際は逆で、自分が困る書き方を、今の時点で知らせてくれる案内係に近いです。

しかも現在の Next.js 16 系では、next lint は削除され、ESLint の flat config を前提にした構成が標準になっています。つまり、昔の記事どおりに設定すると少しズレることがあります。ここを最初に押さえておくと、あとでかなり楽になります。

ESLint とは何か

一言でいえば「コードの見張り役」

ESLint は、コードを実行する前に「危なそうな書き方」「読みにくい書き方」「ルールから外れた書き方」を検出する静的解析ツールです。ESLint 公式の Getting Started でも、主な目的は一貫性の維持とバグ回避だと説明されています。

たとえば、次のようなコードを考えます。

const userName = 'Tomoya'
const unusedValue = 123

console.log(userName)

この unusedValue は宣言されていますが使われていません。JavaScript としては動くこともありますが、ESLint は「これ、本当に必要ですか」と教えてくれます。こういう小さな注意が積み重なると、コードはかなり読みやすくなります。ESLint のルール体系は「問題」「提案」「レイアウト」などに分かれており、ルールごとに警告やエラーを出せます。

フォーマッタとは役割が違う

ここは初心者がよく混同する点です。

ESLint は「この書き方は危ない」「この変数は使っていない」「このルールに違反している」といった 品質チェック が中心です。一方で、単純な空白や改行の整形は別のツールと分担することもあります。ESLint 自体にも fixable なルールはありますが、役割の中心は静的解析です。ESLint 公式も rule の目的を「期待に合っているか検証すること」と説明しています。

Next.js で ESLint が重要な理由

React と Next.js 特有のミスを拾える

Next.js の eslint-config-next には、@next/eslint-plugin-next のルールが含まれています。たとえば、内部遷移での <a> の扱い、<img> 使用の警告、next/script の使い方、<head> の扱いなど、Next.js らしい落とし穴を検出できます。公式の ESLint 設定ページにも、どのルールが含まれるか一覧があります。

たとえば次のようなコードです。

export default function Page() {
  return <img src="/logo.png" alt="logo" />
}

これ自体は JSX として書けます。ですが Next.js では、next/image を使う方が LCP や帯域の観点で望ましいとされ、@next/next/no-img-element が警告対象になります。こういう「動くけれど、よりよい書き方がある」を拾ってくれるのが、Next.js と ESLint の組み合わせの強みです。

開発初期ほど効果が大きい

初心者の段階では、「まず動けばよい」と感じるのは自然です。

ただ、最初の癖がそのまま残ることも多いです。ESLint を初期設定から入れておくと、あとで直すより先に学べる という利点があります。Next.js 公式も、コードエディタ上で警告やエラーを見られる統合を推奨しています。

現在の標準は Flat Config

ESLint v9 では flat config が既定

ESLint 公式は、v9.0.0 から flat config が既定の設定形式 になったと案内しています。従来の .eslintrc.* 系は deprecated です。ESLint の migration guide でも、eslint.config.js などの flat config ファイルを使う流れが説明されています。

つまり、今から始めるなら、まず意識したい設定ファイルはこれです。

eslint.config.mjs

昔の解説で .eslintrc.json.eslintrc.js を見かけても、それは古い流儀の可能性があります。今の Next.js 16 系と ESLint v9 系では、flat config を前提に読む方が安全です。

Next.js 16 では next lint が削除

Next.js の公式 ESLint 設定ページには、Starting with Next.js 16, next lint is removed と明記されています。Next.js 16 のアップグレードガイドにも next lint の削除が載っています。

ここはかなり大事です。

古い教材だと「next lint を実行してください」と書かれていることがありますが、現在の標準は ESLint CLI を直接使う形です。つまり、今は次のように実行するのが基本です。

pnpm exec eslint .

または npm なら、package.json に script を書いて呼ぶ形が自然です。

最初に入れるパッケージ

基本のインストール

Next.js 公式の ESLint 設定ページでは、最初の手順として eslinteslint-config-next を開発依存に追加する方法が案内されています。

pnpm の例は次です。

pnpm add -D eslint eslint-config-next

npm ならこうです。

npm install -D eslint eslint-config-next

この時点で、ESLint 本体と Next.js 向けの共有設定を入れていることになります。Next.js 公式によれば、eslint-config-next には Next.js、React、React Hooks の推奨ルール群が含まれます。

最小構成の eslint.config.mjs

まずは公式どおりの形で十分

Next.js 公式が案内している flat config の基本形は次です。core-web-vitals を使う構成で、.nextoutbuildnext-env.d.ts などの ignore が入っています。

import { defineConfig, globalIgnores } from 'eslint/config'
import nextVitals from 'eslint-config-next/core-web-vitals'

const eslintConfig = defineConfig([
  ...nextVitals,
  globalIgnores([
    '.next/**',
    'out/**',
    'build/**',
    'next-env.d.ts',
  ]),
])

export default eslintConfig

この設定の読み方は、次のとおりです。

  • defineConfig(...):ESLint の flat config を定義するための関数です。
  • nextVitalseslint-config-next/core-web-vitals を読み込んでいます。これは base 設定に加え、Core Web Vitals に影響する一部ルールを warning ではなく error に引き上げる構成です。Next.js 公式はこれを most projects に推奨 しています。
  • globalIgnores([...]):lint 対象から外すパスをまとめています。ビルド成果物や生成ファイルを除外するためです。

core-web-vitals を使う理由

Next.js 公式は eslint-config-nexteslint-config-next/core-web-vitals の2系統を示し、後者は Core Web Vitals に影響するルールを warning から error に引き上げると説明しています。さらに most projects には core-web-vitals を推奨 としています。

初心者にもこの選択は悪くありません。

なぜなら、「動くけれど、あとで UX や性能に響く書き方」を早めに止めやすいからです。最初から少しだけ厳しめにしておく方が、後から習慣を変えるより楽なことが多いです。

TypeScript プロジェクトではどうするか

TypeScript 向け設定を追加できる

Next.js 公式の ESLint 設定ページでは、TypeScript プロジェクト向けに eslint-config-next/typescript を追加する形が案内されています。

import { defineConfig, globalIgnores } from 'eslint/config'
import nextVitals from 'eslint-config-next/core-web-vitals'
import nextTs from 'eslint-config-next/typescript'

const eslintConfig = defineConfig([
  ...nextVitals,
  ...nextTs,
  globalIgnores([
    '.next/**',
    'out/**',
    'build/**',
    'next-env.d.ts',
  ]),
])

export default eslintConfig

この構成にすると、Next.js 向けルールに加えて TypeScript 向けの lint ルールも入ります。Next.js の create-next-app --typescript でも、この TypeScript lint 設定が加わると公式に説明されています。

まずはここまでで十分

初心者の段階では、TypeScript lint の細部までは無理に掘らなくて大丈夫です。

大切なのは、「Next.js 用のルール」と「TypeScript 用のルール」を別レイヤーとして足していると理解することです。この視点があると、後でルールを調整する時も混乱しにくくなります。

package.jsonには何を書くか

実行用 script を用意する

現在の Next.js 16 系では next lint は使わないため、ESLint CLI を直接呼ぶ script を書くのが自然です。Next.js 公式の install 例にも lint: "eslint" が示されています。

たとえば次のようにします。

{
  "scripts": {
    "dev": "next dev",
    "build": "next build",
    "start": "next start",
    "lint": "eslint ."
  }
}

これで次のコマンドが使えます。

npm run lint

または pnpm なら、

pnpm lint

こうしておくと、チーム内でも「lint はこの入口から」という共通認識を作れます。

実際にどんなエラーが出るのか

使っていない変数

たとえば次のようなコードです。

const message = 'hello'
const unusedValue = 123

console.log(message)

この unusedValue は未使用です。ESLint はこうした無駄や見落としを警告できます。ESLint のルール群には possible problems や suggestions があり、未使用変数のような典型的な問題を拾います。

Next.js らしい警告

export default function Page() {
  return <img src="/hero.png" alt="hero" />
}

この場合、Next.js のルールでは next/image を使うよう促されることがあります。Next.js 公式のルール一覧には @next/next/no-img-element が含まれており、LCP や帯域の観点から <img> を避ける意図が示されています。

修正版のイメージはこうです。

import Image from 'next/image'

export default function Page() {
  return <Image src="/hero.png" alt="hero" width={1200} height={630} />
}

ここで感じてほしいのは、ESLint は「ダメです」で終わるのではなく、より Next.js らしい書き方へ誘導する役割もある、ということです。

ignore の考え方

生成物は lint 対象から外す

Next.js 公式の設定例では、.next/**out/**build/**next-env.d.ts を ignore に入れています。これらは生成物や自動生成ファイルであり、通常は自分で直接メンテナンスする対象ではないからです。

つまり、「自分が書くコードを lint したい」のであって、「ツールが生成したファイルまで lint したい」わけではありません。ここを分けて考えると、ignore の意味がかなり分かりやすくなります。

ルールはどう調整するのか

ESLint はルールごとに強さを変えられる

ESLint 公式では、flat config の中で rules を設定し、各ルールをどのように適用するか調整できると説明しています。

たとえば、あるルールを warning にしたり error にしたりできます。

import { defineConfig } from 'eslint/config'
import nextVitals from 'eslint-config-next/core-web-vitals'

const eslintConfig = defineConfig([
  ...nextVitals,
  {
    rules: {
      'no-console': 'warn',
    },
  },
])

export default eslintConfig

この例では console.log を禁止まではしないが、警告は出すという設定です。

初心者のうちは、まず公式の共有設定を使い、必要が出てから少しずつ上書きする くらいがちょうどよいです。

最初からルールを盛りすぎない

ここは実務でも大事です。

厳しくしすぎると、lint の赤字だらけで学習意欲が落ちることがあります。Next.js 公式の共有設定をベースにし、必要なものだけ少しずつ足す方が安定します。特に学習初期は、「lint が通る体験」を増やす方が前に進みやすいです。これは一般的な運用上の考え方です。

モノレポではrootDirを使うことがある

Next.js アプリがルートにない場合

Next.js 公式では、モノレポのようにルート直下に Next.js アプリがない場合、@next/eslint-plugin-nextsettings.next.rootDir で場所を教えられると説明しています。rootDir はパス、glob、配列で指定できます。

たとえば次のような形です。

import { defineConfig } from 'eslint/config'
import eslintNextPlugin from '@next/eslint-plugin-next'

const eslintConfig = defineConfig([
  {
    files: ['**/*.{js,jsx,ts,tsx}'],
    plugins: {
      next: eslintNextPlugin,
    },
    settings: {
      next: {
        rootDir: 'packages/my-app/',
      },
    },
  },
])

export default eslintConfig

初心者のうちはここまで必須ではありません。

ただ、「アプリが深い場所にあるときは設定が増えることがある」と知っているだけで、将来の見通しがかなり変わります。

よくある誤解

ESLint を入れればバグがゼロになる

そこまではいきません。

ESLint は静的解析ツールであり、コードのパターンやルール違反を検出するものです。すべての実行時バグを防ぐわけではありません。けれど、防げるミスをかなり手前で止められる ので価値が大きいです。ESLint 公式も、目的は一貫性とバグ回避だと説明しています。

とにかくルールを厳しくすればよい

これも違います。

ルールはチームや学習段階に合わせて調整するものです。最初から厳しすぎると、lint の意味を理解する前に疲れてしまいます。まずは eslint-config-next/core-web-vitals と、必要なら eslint-config-next/typescript で始めるのが素直です。

古い next lint の記事でもそのまま読める

これは危険です。

Next.js 16 では next lint が削除されています。現在は ESLint CLI で動かすのが基本です。

実践

まずは最小構成で lint を通す

  1. eslinteslint-config-next を入れる
  2. eslint.config.mjs を作る
  3. package.jsonlint script を書く
  4. npm run lint または pnpm lint を実行する

最小コードは次の組み合わせです。

eslint.config.mjs

import { defineConfig, globalIgnores } from 'eslint/config'
import nextVitals from 'eslint-config-next/core-web-vitals'

export default defineConfig([
  ...nextVitals,
  globalIgnores([
    '.next/**',
    'out/**',
    'build/**',
    'next-env.d.ts',
  ]),
])

package.json

{
  "scripts": {
    "lint": "eslint ."
  }
}

実行コマンド

npm run lint

これでエラーや警告が出たら、まずは「失敗」ではなく「検査機が働いている」と受け取るのが大事です。

練習問題

問1

ESLint の主な役割として最も適切なものはどれですか。

A. Web サイトを自動公開する

B. JavaScript / TypeScript コードの問題や一貫性を検査する

C. 画像を自動圧縮する

D. データベースを自動作成する

答え

B

解説

ESLint 公式は、ESLint をコード内のパターンを識別・報告し、一貫性を高め、バグを避けるためのツールだと説明しています。

問2

現在の ESLint v9 系で既定の設定形式として正しいものはどれですか。

A. .eslintrc 形式 B. Flat config C. package.json だけ D. YAML のみ

答え

B

解説

ESLint 公式は、v9.0.0 から flat config が既定の設定形式になったと案内しています。

問3

Next.js 16 で削除されたコマンドはどれですか。

A. next dev B. next start C. next lint D. next build

答え

C

解説

Next.js 公式の ESLint 設定ページでは、Next.js 16 から next lint が削除されたと明記されています。

問4

Next.js 公式が most projects に推奨している ESLint 構成はどれですか。

A. eslint-config-next/core-web-vitals B. ルールなし C. eslint-config-airbnb のみ D. next lint のみ

答え

A

解説

Next.js 公式は eslint-config-next/core-web-vitals を most projects に推奨しており、Core Web Vitals に影響する一部ルールを warning から error に引き上げると説明しています。

問5

TypeScript プロジェクトで Next.js の ESLint 設定に追加できる構成として正しいものはどれですか。

A. eslint-config-next/typescript B. eslint-config-next/database C. eslint-config-next/images D. eslint-config-next/router-only

答え

A

解説

Next.js 公式では、TypeScript プロジェクト向けに eslint-config-next/typescript を追加する構成が案内されています。

まとめ

ESLint は、コードを窮屈にするための道具ではありません。

危ない書き方や読みにくい書き方を、実行前に知らせてくれる保険です。Next.js は eslint-config-next を提供しており、React や Next.js の落とし穴を含めて検査しやすくしています。しかも現在は flat config が標準で、Next.js 16 では next lint ではなく ESLint CLI を直接使う流れになっています。

最初に押さえたいのは次の5点です。

  • ESLint はコードの一貫性と問題検出のための静的解析ツールである。
  • 現在の標準設定形式は flat config である。
  • Next.js 16 では next lint は削除されている。
  • まずは eslint-config-next/core-web-vitals を土台にするのが自然である。
  • TypeScript を使うなら eslint-config-next/typescript を追加できる。

ここまで腹落ちすれば、ESLint は怖い赤字製造機ではなくなります。

むしろ、「いまのうちに直せる場所を教えてくれる、少し口うるさいが頼れる先輩」くらいに見えてきます。その見え方になると、開発はかなり安定します。

参考文献

  • Next.js Documentation, Configuration: ESLint.
  • Next.js Blog, Next.js 16.
  • Next.js Documentation, Upgrading: Version 16.
  • Next.js Documentation, Getting Started: Installation.
  • ESLint Documentation, Getting Started.
  • ESLint Documentation, Configuration Migration Guide.
  • ESLint Documentation, Configuration Files.
  • ESLint Documentation, Configure Rules.
  • ESLint Documentation, Rules Reference.
教材トップへ戻る