React × TypeScriptにおけるESLintとPrettierの設定

## 初めに

今回はReact × TypeScriptプロジェクトに、AirbnbスタイルのESLintとPrettierを設定していきます。

Airbnbスタイルを選定した理由は、使用率が世界で最も高いからです。

また、スタンダードなスタイルに慣れておけば他のスタイルにも適応しやすいだろうという安易な考えのもと進めていきます。

また、今回は必要最低限の最小構成で構築していきますので、気になるところがありましたら公式ドキュメントなどを参考に設定を追加してあげてください。

## ESLintとは

ESLintはJavaScriptの静的解析ツールで、コードの問題点（バグの可能性があるコードなど）を検知してくれます。

コードを実行する前にバグを見つけてくれるので、後になってバグが起きている箇所がわからないという事態を未然に防いでくれます。

ちなみに、lintは直訳すると「糸くず」という意味で、「ESLint」は乾燥機の糸くずを取り除くさまをプログラミング用語として流用したものだそうです。

## ESLintのスタイルについて

現在、ESLintのスタイルとしては以下の３つが主流です。

- [Airbnb](https://github.com/airbnb/javascript)
- [Standard](https://github.com/standard/standard)
- [Google](https://github.com/google/eslint-config-google)

その中でも今回は現時点で最も使用率が高い「airbnb」スタイルで設定を進めていきます。

それぞれのスタイルの使用率比較は以下を参照してください。　

[Comparing eslint-config-airbnb vs. eslint-config-google vs. standard](https://npmcompare.com/compare/eslint-config-airbnb,eslint-config-google,standard)

[eslint-config-airbnb vs eslint-config-google vs standard | npm trends](https://npmtrends.com/eslint-config-airbnb-vs-eslint-config-google-vs-standard)

## ESLintの初期設定

まずは、ESLintの初期設定をするために、以下のコマンドを入力します！

```bash
npm init @eslint/config
```

このコマンドを実行すると、質問形式でconfigファイルの作成が始まります。

今回は「React × TypeScript × airbnb」でプロジェクトを作るので、以下の流れで設定を進めていきます。

- ESLintの適応範囲を選択

```bash
// 「構文チェック」「問題の発見」「スタイル強制」を適用

? How would you like to use ESLint? … 
  To check syntax only
  To check syntax and find problems
**❯ To check syntax, find problems, and enforce code style**
```

- モジュールのインポート形式を選択

```bash
// JavaScriptを適用

? What type of modules does your project use? … 
**❯ JavaScript modules (import/export)**
  CommonJS (require/exports)
  None of these
```

- フレームワークを選択

```bash
// Reactを適用

? Which framework does your project use? … 
**❯ React**
  Vue.js
  None of these
```

- TypeScript使用設定

```bash
// Yesを選択

? Does your project use TypeScript? › No / **Yes**
```

- ESLintのコーディングスタイルを選択

```bash
// ポピュラーなスタイルを選択

? How would you like to define a style for your project? …
**❯ Use a popular style guide**
  Answer questions about your style
  Inspect your JavaScript file(s)
```

```bash
// airbnbスタイルを適用

? Which style guide do you want to follow? … 
**❯ Airbnb: https://github.com/airbnb/javascript**
  Standard: https://github.com/standard/standard
  Google: https://github.com/google/eslint-config-google
  XO: https://github.com/xojs/eslint-config-xo
```

- configファイルの形式

```bash
// JavaScriptを適用

? What format do you want your config file to be in? … 
**❯ JavaScript**
  YAML
  JSON
```

- インストール確認

```bash
// Yesを選択

eslint-plugin-react@^7.28.0 @typescript-eslint/eslint-plugin@latest eslint-config-airbnb@latest eslint@^7.32.0 
|| ^8.2.0 eslint-plugin-import@^2.25.3 eslint-plugin-jsx-a11y@^6.5.1 eslint-plugin-react-hooks@^4.3.0 @typescript-eslint/parser@latest
? Would you like to install them now? › No / **Yes**
```

- パッケージマネージャを選択

```bash
// npmを適用

? Which package manager do you want to use? … 
**❯ npm**
  yarn
  pnpm
```

以上でESLintの基本的な初期設定は完了です。

今回は、TypeScriptを使用しているので、airbnb のTypeScript版パッケージもインストールしておきます。

```bash
npm i --save-dev eslint-config-airbnb-typescript
```

公式記事に沿って、以下の設定を.eslinttrc.jsに追記していきます。

```bash
{ 
  extends: ['airbnb', 'airbnb-typescript'], 
	parserOptions: { 
	    project: './tsconfig.json' 
	 } 
}
```

詳しい設定方法は、以下の公式ページを参照ください

[eslint-config-airbnb-typescript](https://www.npmjs.com/package/eslint-config-airbnb-typescript)

## ESLintとPrettierを一緒に使う

次にPretteirの設定をします。

プロジェクトに ESLintを導入している場合、Prettier によるフォーマットと ESLint による解析ルールが競合するので、ESLintのフォーマット機能を無効化する必要があります。

これに対して、Prettier チームが正式に提供しているライブラリ「eslint-config-prettier」をインストールすることで、競合を防ぐことができます。

では、以下のコマンドを実行して、Prettierをインストールします。

```bash
npm install --save-dev prettier eslint-config-prettier
```

次にprettierの設定ファイルとなる「.prettierrc.js」を作成してフォーマットを設定していきます。

```bash
module.exports = {
	semi: true, // 行末のセミコロンは省略しない
	singleQuote: true // 引用符にはシングルクォートを使う
}
```

それでは、Prettierを.eslintrc.jsに読み込んでいきます。

１つ注意して頂きたいのが、Prettierの記述はextendsの最後に追加してくだい。

ESLintの設定をPrettierで上書きする必要があるためです。以下コードです。

```bash
extends: [
	"plugin:react/recommended", 
	"airbnb", 
	'airbnb-typescript', 
	"prettier"
],
```

以上でPrettierの設定は終わりです！

## ESLintの詳細設定

ここまでで基本的な実装は終了なのですが、このままESLintを実行したら、静的解析に引っ掛かりエラーが沢山出ました。。

なので最後に、.eslintrc.jsにESLintの詳細設定を追記していきます。

最終的な.eslintrc.jsは以下のようになりました。

```bash
module.exports = {
  env: {
    browser: true,
    es2021: true,
  },
  extends: ["plugin:react/recommended", "airbnb", 'airbnb-typescript', "prettier"],
  parser: "@typescript-eslint/parser",
  parserOptions: {
    project: './tsconfig.json',
    ecmaFeatures: {
      jsx: true
    },
    ecmaVersion: "latest",
    sourceType: "module",
  },
  plugins: ["react", "@typescript-eslint"],
  rules: {
    'import/prefer-default-export': 'off', // named exportがエラーになるので使えるようにoff
    'import/extensions': [ // importのときに以下の拡張子を記述しなくてもエラーにしない
      'error',
      {
        js: 'never',
        jsx: 'never',
        ts: 'never',
        tsx: 'never',
      },
    ],
    'react/function-component-definition': [ // アロー関数以外受け付けない設定
      2,
      {
        namedComponents: 'arrow-function',
        unnamedComponents: 'arrow-function',
      },
    ],
    'react/jsx-filename-extension': [ //jsx形式のファイル拡張子をjsxもしくはtsxに限定
      'error',
      {
        extensions: ['.jsx', '.tsx'],
      },
    ],
  },
  settings: {
    'import/resolver': { //importするファイルをjsだけではなく、tsを含むファイルを許可する
      node: {
        paths: ['src'],
        extensions: ['.js', '.jsx', '.ts', '.tsx'],
      },
    },
  },
};
```

自分好みの設定ファイルを作りたい方は、以下の記事にて詳しい設定方法をご確認ください。

## 実行

では実際に実行してみましょう！

実行に際して、ESLintとPrettierの実行コマンドをpackage.jsonに登録しておきます。これで、npmコマンドから簡単に実行が可能になります。

```bash
"scripts": {
    "build": "webpack",
    "start": "webpack serve --open",
		// 以下を追記
    "lint": "eslint --ext .jsx,.js,.tsx,.ts src/",　// ESLintによる解析
    "fmt": "prettier --write src/**/*"　// Prettierによるフォーマット
  },
```

これでAirbnbスタイルベースのESLintとPrettierの設定は完了です。お付き合いいただきありがとうございました！

 **参考**
---

[https://prettier.io/docs/en/options.html](https://prettier.io/docs/en/options.html)

[https://npmcompare.com/compare/eslint-config-airbnb,eslint-config-google,standard](https://npmcompare.com/compare/eslint-config-airbnb,eslint-config-google,standard)

[https://npmtrends.com/eslint-config-airbnb-vs-eslint-config-google-vs-standard](https://npmtrends.com/eslint-config-airbnb-vs-eslint-config-google-vs-standard)

[https://yumegori.com/vscode_react_typescript_eslint_prettier#chapter-0](https://yumegori.com/vscode_react_typescript_eslint_prettier#chapter-0)

[https://maku.blog/p/avssq37/](https://maku.blog/p/avssq37/)

[https://prettier.io/docs/en/options.html](https://prettier.io/docs/en/options.html)