Prettier 17 ๐จ eslint-plugin-prettier โ Running Prettier as an ESLint rule
eslint-plugin-prettier inverts the relationship between the two tools. Instead of Prettier running as a separate command and ESLint running separately, the plugin runs Prettier inside ESLint and reports formatting differences as individual ESLint issues . The prettier/prettier rule becomes the mechanism: when a file does not match Prettier’s output, ESLint reports an error on the specific line and column where the formatting diverges. Running eslint --fix then applies Prettier’s formatting along with any other fixable ESLint rules in a single pass .
The plugin does not replace Prettier or ESLint. It requires both to be installed, and it works best when combined with eslint-config-prettier to disable the formatting rules that would otherwise conflict. The recommended configuration does exactly that: it enables the prettier/prettier rule, pulls in eslint-config-prettier to disable conflicting rules, and disables two specific rules (arrow-body-style and prefer-arrow-callback) that interact badly with the plugin’s autofix . The result is a single lint command that enforces both code quality and formatting.
Key point: The plugin makes formatting a lint error. It requires Prettier and ESLint to be installed separately, and its recommended config must be placed last in the ESLint configuration so that eslint-config-prettier can disable conflicting rules. The arrow-body-style and prefer-arrow-callback rules are disabled by the recommended config because they can produce invalid code during autofix when combined with the plugin.
Why the plugin exists
The single-command problem. The separate-tools patternโESLint for quality, Prettier for formattingโrequires two commands, two editor integrations, and two CI steps. The plugin collapses them. eslint --fix applies both the ESLint fixes and the Prettier formatting. The developer runs one command, and the output is both correct and consistently formatted. The plugin’s documentation frames this as the primary benefit: the prettier/prettier rule reports formatting differences as ESLint issues, and ESLint’s autofix applies the Prettier output .
The visibility problem. When Prettier runs as a separate step, formatting errors are invisible to the linter. A developer who only runs eslint sees code-quality issues but not formatting issues. The plugin makes formatting issues visible in the same report as the lint issues. A trailing space becomes an ESLint error on the line where it appears, not a separate Prettier failure that the developer discovers later .
The autofix conflict problem. The plugin’s autofix runs Prettier’s formatter and then applies the result as an ESLint fix. This works for most rules, but two ESLint rulesโarrow-body-style and prefer-arrow-callbackโcan produce invalid code when their autofix runs alongside the plugin’s fix. The issue is a bug in ESLint’s autofix that can leave a missing closing parenthesis . The recommended config disables both rules to prevent this. A project that re-enables them accepts the risk of invalid code after --fix.
The trade-off. The plugin adds overhead to every lint run. Prettier must format each file inside ESLint’s process, which is slower than running Prettier as a separate step with its own optimizations. The plugin also couples the formatting configuration to the ESLint configuration, which means an editor that reads .prettierrc but not the ESLint config can produce different results from the command line . The recommended pattern is to keep formatting options in a .prettierrc file and let the plugin read it, so that the editor and the linter agree.
a. Configuring the plugin in flat config
ESLint 9+ uses flat config. The eslint-plugin-prettier/recommended import is the entry point, and it must be placed last in the exported array.
// eslint.config.mjs โ flat config with eslint-plugin-prettier
import eslintPluginPrettierRecommended from "eslint-plugin-prettier/recommended";
export default [
{
files: ["**/*.{js,jsx,ts,tsx}"],
rules: {
// Code-quality rules stay enabled.
// The plugin does not disable these.
"no-unused-vars": "error",
"eqeqeq": "error",
},
},
// The recommended config must be last.
// It enables prettier/prettier and disables conflicting rules.
eslintPluginPrettierRecommended,
];
The recommended config enables the prettier/prettier rule, pulls in eslint-config-prettier, and disables arrow-body-style and prefer-arrow-callback . The placement is the mechanism: if the config is not last, a later config can re-enable a formatting rule and the conflict returns. The plugin’s documentation states this explicitly: “Put eslint-plugin-prettier/recommended last in flat config arrays” .
// eslint.config.mjs โ a broken configuration
import eslintPluginPrettierRecommended from "eslint-plugin-prettier/recommended";
export default [
eslintPluginPrettierRecommended,
{
// โ This config re-enables a formatting rule
// AFTER the recommended config disabled it.
rules: { indent: ["error", 2] },
},
];
The second configuration object overrides the indent rule that the recommended config disabled. The rule is active again, and it will conflict with Prettier’s indentation. The fix is to move the recommended config to the end of the array.
b. Configuring the plugin in legacy config
Legacy .eslintrc configuration uses the extends array. The correct shareable-config name is "plugin:prettier/recommended".
// .eslintrc.json โ legacy config with eslint-plugin-prettier
{
"extends": [
"eslint:recommended",
// The recommended config must be last.
// It enables prettier/prettier and eslint-config-prettier.
"plugin:prettier/recommended"
],
"rules": {
"no-unused-vars": "error",
"eqeqeq": "error"
}
}
The legacy recommended config does the same three things as the flat config: enables the rule, disables the conflicting rules, and pulls in eslint-config-prettier . The placement rule is the same. A shareable config added after "plugin:prettier/recommended" can re-enable a formatting rule and restore the conflict.
Complete Example Session
// ============================================
// PART 1: THE INSTALLATION
// ============================================
// npm install --save-dev eslint prettier eslint-plugin-prettier eslint-config-prettier
//
// The plugin does not install Prettier or ESLint.
// Both must be installed separately.
// eslint-config-prettier is pulled in by the recommended config,
// but installing it explicitly is the documented pattern.
// ============================================
// PART 2: THE FLAT CONFIG
// ============================================
// eslint.config.mjs
import eslintPluginPrettierRecommended from "eslint-plugin-prettier/recommended";
export default [
{
files: ["**/*.{js,jsx,ts,tsx}"],
rules: {
"no-unused-vars": "error",
"eqeqeq": "error",
},
},
// The recommended config must be last.
eslintPluginPrettierRecommended,
];
// ============================================
// PART 3: THE LEGACY CONFIG
// ============================================
// .eslintrc.json
// {
// "extends": ["eslint:recommended", "plugin:prettier/recommended"],
// "rules": {
// "no-unused-vars": "error",
// "eqeqeq": "error"
// }
// }
// ============================================
// PART 4: THE PRETTIER CONFIGURATION
// ============================================
// .prettierrc.json
{
"semi": true,
"singleQuote": true,
"printWidth": 100
}
// The plugin reads the .prettierrc file by default.
// Keeping formatting options in .prettierrc means
// editor integrations and the linter use the same settings.
// ============================================
// PART 5: THE LINT AND FIX COMMANDS
// ============================================
// package.json
{
"scripts": {
"lint": "eslint .",
"lint:fix": "eslint . --fix"
}
}
// `npm run lint` reports formatting differences as errors.
// `npm run lint:fix` applies the Prettier formatting
// along with any other ESLint fixes.
// ============================================
// PART 6: THE FORMATTING ERROR
// ============================================
// src/app.js โ before fixing
const greeting = "hello"; // trailing semicolon, double quotes
// `eslint .` reports:
// error Delete `;` prettier/prettier
// error Replace `"hello"` with `'hello'` prettier/prettier
// The errors are attributed to the prettier/prettier rule,
// not to ESLint's own formatting rules.
// ============================================
// PART 7: THE AUTOFIX
// ============================================
// src/app.js โ after `eslint --fix`
const greeting = 'hello'
// The semicolon is removed (semi: false? No, semi: true means kept).
// The quotes are changed to single quotes.
// The output matches Prettier's formatting.
// ============================================
// PART 8: THE DISABLED RULES
// ============================================
// The recommended config disables:
// - arrow-body-style
// - prefer-arrow-callback
//
// These rules can produce invalid code during autofix
// when combined with prettier/prettier.
// The plugin's documentation explains the issue.
// ============================================
// PART 9: THE ARROW FUNCTION CASE
// ============================================
// Without the disabled rules, this code:
const fn = () => {
return 42;
};
// Could be autofixed by arrow-body-style to:
const fn = () => 42;
// If prettier/prettier also runs its autofix,
// a bug in ESLint's autofix can produce:
const fn = () => 42; // valid
// or in some cases:
const fn = () => 42 // missing closing paren
// The recommended config disables the rule to prevent this.
// ============================================
// PART 10: THE VERIFICATION
// ============================================
// [ ] eslint-plugin-prettier and eslint-config-prettier are installed.
// [ ] The recommended config is last in the ESLint configuration.
// [ ] The .prettierrc file contains the formatting options.
// [ ] `eslint .` reports formatting differences as prettier/prettier errors.
// [ ] `eslint . --fix` applies the formatting.
// [ ] arrow-body-style and prefer-arrow-callback are disabled.
The ten parts covered the installation, the flat config, the legacy config, the Prettier configuration, the lint and fix commands, the formatting error, the autofix, the disabled rules, the arrow function case, and the verification checklist. The through-line is that the plugin makes formatting a lint rule, and the placement and the disabled rules are what make it work.
Quick Reference
Installation
| Command | Purpose |
|---|---|
npm install -D eslint prettier eslint-plugin-prettier eslint-config-prettier | Install all four packages |
Configuration placement
| Config format | Import / extend | Position |
|---|---|---|
| Flat config | import eslintPluginPrettierRecommended from "eslint-plugin-prettier/recommended" | Last in the exported array |
| Legacy config | "plugin:prettier/recommended" in extends | Last in the extends array |
What the recommended config does
| Action | Effect |
|---|---|
Enables prettier/prettier | Reports formatting differences as ESLint errors |
Pulls in eslint-config-prettier | Disables conflicting formatting rules |
Disables arrow-body-style | Prevents autofix bug |
Disables prefer-arrow-callback | Prevents autofix bug |
Commands
| Command | Effect |
|---|---|
eslint . | Reports formatting and quality issues |
eslint . --fix | Applies Prettier formatting and other fixes |
Best Practices
โ Do This:
// Place the recommended config last in flat config
export default [ /* rules */, eslintPluginPrettierRecommended]; // โ
// Place "plugin:prettier/recommended" last in legacy extends
"extends": ["eslint:recommended", "plugin:prettier/recommended"] // โ
// Keep formatting options in .prettierrc
// { "semi": true, "singleQuote": true } // โ
// Run eslint --fix to apply formatting
eslint . --fix // โ
โ Don’t Do This:
// Place the recommended config before other configs
export default [eslintPluginPrettierRecommended, { rules: {} }]; // โ
// Re-enable arrow-body-style after the recommended config
{ rules: { "arrow-body-style": "error" } } // after prettier // โ
// Pass formatting options through ESLint config instead of .prettierrc
// Editor extensions read .prettierrc, not ESLint config // โ
Common Pitfalls
| Pitfall | Why It Happens | Fix |
|---|---|---|
| Formatting errors are not reported | The recommended config is not included | Add it to the config |
| Conflicts persist after adding the plugin | The recommended config is not last | Move it to the last position |
eslint --fix produces invalid code | arrow-body-style or prefer-arrow-callback re-enabled | Leave them disabled |
| Editor formatting differs from lint output | Formatting options passed through ESLint, not .prettierrc | Move options to .prettierrc |
| Prettier is not installed | The plugin does not install Prettier | npm install -D prettier |
Real-World Examples
1. Flat config import
import eslintPluginPrettierRecommended from "eslint-plugin-prettier/recommended";
2. Flat config placement
export default [{ rules: {} }, eslintPluginPrettierRecommended];
3. Legacy extends
"extends": ["eslint:recommended", "plugin:prettier/recommended"]
4. Prettier config
{ "semi": true, "singleQuote": true, "printWidth": 100 }
5. Lint command
eslint .
6. Fix command
eslint . --fix
7. Disabled rule
// "arrow-body-style" and "prefer-arrow-callback" are off
8. Formatting error
// error Delete `;` prettier/prettier
9. Autofix output
const greeting = 'hello'
10. Editor integration
// The editor reads .prettierrc, not the ESLint config
Visual
The Plugin’s Role
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ WHAT THE PLUGIN DOES โ
โ โ
โ Source code ESLint output โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ const x = "hello"; โ โ error: Delete `;` โ โ
โ โ โ โโโโถ โ error: Replace `"` โ โ
โ โ โ โ with `'` โ โ
โ โ โ โ rule: prettier/prettierโ โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ
โ The plugin runs Prettier inside ESLint. โ
โ The formatting differences are reported as lint errors. โ
โ `--fix` applies the formatting. โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
The Recommended Config
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ WHAT eslint-plugin-prettier/recommended INCLUDES โ
โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ 1. Enables prettier/prettier rule โ โ
โ โ 2. Pulls in eslint-config-prettier โ โ
โ โ (disables conflicting formatting rules) โ โ
โ โ 3. Disables arrow-body-style โ โ
โ โ 4. Disables prefer-arrow-callback โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ
โ The config must be placed last. โ
โ If another config re-enables a formatting rule, โ
โ the conflict returns. โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
The Autofix Bug
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ WHY arrow-body-style IS DISABLED โ
โ โ
โ Source: โ
โ const fn = () => { return 42; }; โ
โ โ
โ arrow-body-style autofix: โ
โ const fn = () => 42; โ
โ โ
โ prettier/prettier autofix runs on the same line. โ
โ A bug in ESLint's autofix can produce: โ
โ const fn = () => 42; // valid โ
โ const fn = () => 42 // missing closing paren โ
โ โ
โ The recommended config disables the rule to prevent this. โ
โ If re-enabled, the risk of invalid code returns. โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
The Placement Rule
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ WHERE THE RECOMMENDED CONFIG GOES โ
โ โ
โ โ
Correct: โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ eslint:recommended โ โ
โ โ plugin:prettier/ โ โ last โ
โ โ recommended โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ
โ โ Wrong: โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ plugin:prettier/ โ โ first โ
โ โ recommended โ โ
โ โโโโโโโโโโโโฌโโโโโโโโโโโ โ
โ โ โ
โ โผ โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ other config โ โ re-enables formatting rule โ
โ โ โ โ conflict returns โ
โ โโโโโโโโโโโโโโโโโโโโโโโ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
Summary
| Item | Value |
|---|---|
| Purpose | Runs Prettier as an ESLint rule |
| Rule name | prettier/prettier |
| Flat config import | eslint-plugin-prettier/recommended |
| Legacy config name | plugin:prettier/recommended |
| Placement | Last in the ESLint configuration |
| Includes | eslint-config-prettier |
| Disables | arrow-body-style, prefer-arrow-callback |
| Requires | Prettier and ESLint installed separately |
Key takeaways:
- The plugin makes formatting a lint error. The
prettier/prettierrule reports formatting differences as individual ESLint issues, andeslint --fixapplies the Prettier formatting along with other fixes. The developer runs one command instead of two . - The recommended config must be last. It enables the rule, pulls in
eslint-config-prettier, and disables the two problematic rules. If another config re-enables a formatting rule after it, the conflict returns. The placement is the mechanism . arrow-body-styleandprefer-arrow-callbackare disabled for a reason. A bug in ESLint’s autofix can produce invalid code when these rules run alongside the plugin’s fix. The recommended config disables them to prevent this. Re-enabling them accepts the risk .- Formatting options belong in
.prettierrc. The plugin reads.prettierrcby default, and editor integrations read it too. Passing formatting options through the ESLint config means the editor and the linter can disagree . - The plugin is not a replacement for Prettier. It requires Prettier to be installed and reports Prettier’s output through ESLint. It does not install Prettier, and it does not format files without
eslint --fix.
Remember: eslint-plugin-prettier is a bridge, not a replacement. It runs Prettier inside ESLint and reports the differences as lint errors, which means one command enforces both code quality and formatting. The bridge works because the recommended config disables the conflicting rules, pulls in eslint-config-prettier, and disables the two rules that break autofix. The placement is the mechanism, and the .prettierrc file is the source of truth for formatting options. A project that places the config correctly and keeps its formatting options in .prettierrc gets the single-command workflow without the conflicts.
Stop using slow, ad-bloated tool sites! ๐คฎ
๐ Search “KandZ Tools” on Google to use many professional utilities for free.
KandZ.me is the ultimate minimalist hub for:
โ
Finance (Mortgage, Interest, Inflation)
โ
Tech (Base64, JSON, Dev Suite, IP)
โ
Health (BMI, BMR, TDEE)
โ
Productivity (Timer, Workspace, QR)
โก๏ธ Fast & Private
๐ No data leaves your device
๐ 100% Free
๐ Use it now: https://tools.kandz.me
๐ Bookmark itโyouโll need it later!