ESLint Configuration for TypeScript React Project ================================================= This document outlines the ESLint configuration used in our TypeScript React project. It provides a robust set of rules and plugins to ensure code quality and consistency. Table of Contents ----------------- 1. `Overview`_ 2. `Prerequisites`_ 3. `Installation`_ 4. `Configuration File`_ 5. `Key Features`_ 6. `Usage`_ 7. `Customization`_ Overview -------- Our ESLint configuration is designed for a TypeScript React project using Vite. It incorporates rules for TypeScript, React, React Hooks, Vitest (for testing), and includes additional plugins for import sorting, accessibility, and code formatting. Prerequisites ------------- - Node.js (version 14 or later recommended) - Yarn or npm - A TypeScript React project (preferably using Vite) Installation ------------ Install the required dependencies by running the following command in your project root: .. code-block:: bash yarn add -D eslint @typescript-eslint/eslint-plugin @typescript-eslint/parser eslint-plugin-react eslint-plugin-react-hooks eslint-plugin-vitest eslint-plugin-testing-library eslint-plugin-import eslint-plugin-jsx-a11y eslint-plugin-prettier eslint-config-prettier eslint-import-resolver-typescript Here's a brief description of each package: - ``eslint``: The core ESLint library - ``@typescript-eslint/eslint-plugin``: ESLint plugin which provides rules for TypeScript codebases - ``@typescript-eslint/parser``: An ESLint parser which leverages TypeScript ESTree to allow for ESLint to lint TypeScript source code - ``eslint-plugin-react``: React specific linting rules for ESLint - ``eslint-plugin-react-hooks``: ESLint plugin which provides rules for React Hooks - ``eslint-plugin-vitest``: ESLint plugin for Vitest, a Vite-native testing framework - ``eslint-plugin-testing-library``: ESLint plugin for Testing Library, providing rules to follow Testing Library best practices - ``eslint-plugin-import``: ESLint plugin with rules that help validate proper imports - ``eslint-plugin-jsx-a11y``: Static AST checker for accessibility rules on JSX elements - ``eslint-plugin-prettier``: Runs Prettier as an ESLint rule and reports differences as individual ESLint issues - ``eslint-config-prettier``: Turns off all rules that are unnecessary or might conflict with Prettier - ``eslint-import-resolver-typescript``: This plugin adds TypeScript support to ``eslint-plugin-import`` Configuration File ------------------ Create a file named ``eslint.config.js`` in your project root with the following content: .. code-block:: javascript import { fixupPluginRules } from '@eslint/compat'; import typescript from '@typescript-eslint/eslint-plugin'; import typescriptParser from '@typescript-eslint/parser'; import react from 'eslint-plugin-react'; import reactHooks from 'eslint-plugin-react-hooks'; import vitestPlugin from 'eslint-plugin-vitest'; import testingLibrary from 'eslint-plugin-testing-library'; import importPlugin from 'eslint-plugin-import'; import jsxA11y from 'eslint-plugin-jsx-a11y'; import prettier from 'eslint-plugin-prettier'; import prettierConfig from 'eslint-config-prettier'; export default [ { files: ['src/**/*.{ts,tsx}'], ignores: ['**/dist/**', '**/node_modules/**', '**/coverage/**'], languageOptions: { parser: typescriptParser, parserOptions: { ecmaVersion: 'latest', sourceType: 'module', project: './tsconfig.json', }, }, plugins: { '@typescript-eslint': fixupPluginRules(typescript), react: fixupPluginRules(react), 'react-hooks': fixupPluginRules(reactHooks), vitest: fixupPluginRules(vitestPlugin), 'testing-library': fixupPluginRules(testingLibrary), import: fixupPluginRules(importPlugin), 'jsx-a11y': fixupPluginRules(jsxA11y), prettier, }, settings: { react: { version: 'detect', }, 'import/parsers': { '@typescript-eslint/parser': ['.ts', '.tsx'], }, 'import/resolver': { typescript: { alwaysTryTypes: true, project: './tsconfig.json', }, }, }, rules: { ...typescript.configs.recommended.rules, ...react.configs.recommended.rules, ...reactHooks.configs.recommended.rules, ...vitestPlugin.configs.recommended.rules, ...testingLibrary.configs.react.rules, ...importPlugin.configs.recommended.rules, ...jsxA11y.configs.recommended.rules, ...prettierConfig.rules, 'prettier/prettier': 'error', 'react/react-in-jsx-scope': 'off', 'react/jsx-uses-react': 'off', '@typescript-eslint/explicit-module-boundary-types': 'off', '@typescript-eslint/no-unused-vars': ['error', { argsIgnorePattern: '^_' }], 'react-hooks/exhaustive-deps': 'warn', 'import/no-unresolved': 'error', 'import/default': 'off', 'import/no-named-as-default': 'off', 'import/no-named-as-default-member': 'off', 'import/order': [ 'error', { groups: ['builtin', 'external', 'internal', 'parent', 'sibling', 'index'], 'newlines-between': 'always', alphabetize: { order: 'asc', caseInsensitive: true }, }, ], 'jsx-a11y/anchor-is-valid': [ 'error', { components: ['Link'], specialLink: ['to'], }, ], }, }, { files: ['src/**/*.test.{ts,tsx}'], rules: { '@typescript-eslint/no-explicit-any': 'off', 'vitest/expect-expect': 'error', 'vitest/no-disabled-tests': 'warn', 'vitest/no-focused-tests': 'error', 'testing-library/await-async-queries': 'error', 'testing-library/no-await-sync-queries': 'error', 'testing-library/no-debugging-utils': 'warn', 'testing-library/no-dom-import': 'off', }, }, { files: ['*.config.ts', 'vite.config.ts'], rules: { 'import/no-extraneous-dependencies': 'off', }, }, ];