Enforcing Uniform Code Formatting in React with ESLint, Prettier, and Husky
Maintaining consistent code style and quality is crucial in any React project, especially as your team or codebase grows. This article will guide you through setting up ESLint, Prettier, and Husky for your React + TypeScript project with a minimal and effective configuration to enforce uniform formatting and linting.
Why enforce uniform formatting?
- Improves readability by applying a consistent style across your codebase
- Reduces code review friction by avoiding style debates
- Prevents bugs and errors early via linting
- Automates formatting to save developer time
Tools overview
- Prettier: An opinionated code formatter that automatically formats your files.
- ESLint: A linting tool that catches code errors and enforces coding standards.
- Husky: A Git hooks manager to run commands like linting and formatting before commits.
- lint-staged: Runs linters only on staged files for faster, focused checks.
Step 1: Install required dependencies
Run this command in your project root to install all required packages:
npm install --save-dev prettier eslint eslint-config-prettier @typescript-eslint/parser @typescript-eslint/eslint-plugin husky lint-staged
This includes:
prettierfor formattingeslintfor core linting functionality@typescript-eslint/parserto let ESLint parse TypeScript syntax (interfaces, types, enums, etc.)@typescript-eslint/eslint-pluginto add TypeScript-specific linting rules and best practiceseslint-config-prettierto disable ESLint rules that might conflict with Prettier formattinghuskyandlint-stagedfor managing Git pre-commit hooks to run linters and formatters automatically
Step 2: Configure Prettier
Create a .prettierrc file in your project root with the following content:
{
"semi": true,
"singleQuote": true,
"printWidth": 80,
"trailingComma": "all",
"endOfLine": "lf"
}
This sets basic formatting rules such as using semicolons, single quotes, and consistent line breaks.
Step 3: Configure ESLint
Create a .eslintrc.json file in the root with this minimal TypeScript-focused config:
{
"env": {
"browser": true,
"es2021": true
},
"extends": [
"eslint:recommended",
"plugin:@typescript-eslint/recommended",
"prettier"
],
"parser": "@typescript-eslint/parser",
"parserOptions": {
"ecmaVersion": 12,
"sourceType": "module"
},
"plugins": ["@typescript-eslint"],
"rules": {}
}
This enables recommended ESLint and TypeScript rules while deferring formatting concerns to Prettier.
Step 4: Setup lint-staged and Husky
Add this to your package.json to tell lint-staged what files to check and fix on commit:
"lint-staged": {
"src/**/*.{js,jsx,ts,tsx}": [
"eslint --fix",
"prettier --write"
]
}
Initialize Husky and add a pre-commit hook:
npx husky install
npx husky add .husky/pre-commit "npx lint-staged"
This runs ESLint and Prettier on your staged files before each commit, helping keep your codebase clean automatically.
Step 5: (Optional) Configure your editor for format on save
If you use VS Code, install the Prettier and ESLint extensions and add the following to your workspace or user settings to format and fix lint issues on save:
{
"editor.formatOnSave": true,
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true
}
}
Future enhancements
- Add React-specific linting rules by installing
eslint-plugin-reactandeslint-plugin-react-hooks. - Integrate stylelint for CSS/Tailwind linting.
- Add testing lint rules (e.g., for Jest).
Conclusion
With just a few dependencies and configuration files, you can automate and enforce consistent code formatting and linting across your React + TypeScript projects. This saves developer time, reduces errors, and improves collaboration—an essential step toward a professional codebase.