@pleaseai/eslint-config is an opinionated ESLint flat config built on top of @antfu/eslint-config. It gives you a single pleaseai() function that wires up linting and formatting for JS/TS/JSX/Vue/JSON/YAML/Markdown out of the box — no Prettier required.
Features
- ESLint flat config format, composable and future-proof
- Auto-fix for formatting — use standalone without Prettier
- TypeScript, JSX, Vue, JSON, YAML, Markdown, TOML, XML, GraphQL, Svelte, Astro, CSS support
- Optional React, Next.js, Svelte, UnoCSS, Astro, Solid, Angular integrations
- Optional formatters for CSS / HTML / Markdown via
eslint-plugin-format - Includes
eslint-plugin-package-jsonconfigs - Auto-detects
.gitignorepatterns - Requires ESLint v10.4.0+
Installation
bun add -D @pleaseai/eslint-config eslintpnpm add -D @pleaseai/eslint-config eslintnpm install -D @pleaseai/eslint-config eslintUsage
Create eslint.config.ts (or eslint.config.mjs) in your project root:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai()That’s it. ESLint will pick it up automatically on the next run.
With Options
pleaseai() accepts the same options as @antfu/eslint-config:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai({
// Override PleaseAI defaults
stylistic: {
indent: 4,
},
// Enable framework support
vue: true,
react: true,
// Add ignores
ignores: [
'**/fixtures',
],
})See Framework Integrations for the full list of framework flags and their peer dependencies.
With Additional Configs
Pass additional flat config items as rest arguments — they’re merged after the PleaseAI preset:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai(
{
typescript: true,
},
{
files: ['**/*.ts'],
rules: {
'no-console': 'warn',
},
},
)Rules Overrides
Every framework integration accepts an overrides object so you can tune rules without replacing the whole preset:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai({
vue: {
overrides: {
'vue/operator-linebreak': ['error', 'before'],
},
},
typescript: {
overrides: {
'ts/consistent-type-definitions': ['error', 'interface'],
},
},
})For overrides that don’t fit a specific integration, pass a second argument with a rules object as shown in With Additional Configs.
NPM Scripts
Add the lint commands to your package.json:
{
"scripts": {
"lint": "eslint .",
"lint:fix": "eslint . --fix"
}
}Run npm run lint to check, or npm run lint:fix to auto-fix.
PleaseAI Defaults
This config wraps @antfu/eslint-config with these PleaseAI-specific defaults:
| Option | Value | Note |
|---|---|---|
stylistic.indent |
2 |
Two-space indent |
stylistic.quotes |
single |
Single quotes |
stylistic.semi |
false |
No trailing semicolons |
typescript |
true |
Enabled out of the box |
gitignore |
true |
Ignores anything in .gitignore |
lessOpinionated |
true |
Disables antfu/if-newline and antfu/curly, enables curly: ['error', 'all'] |
antfu/top-level-function |
Re-enabled | Prefer function declarations at top level |
test/prefer-lowercase-title |
Disabled | Test titles can start with any case |
The lessOpinionated: true + curly: ['error', 'all'] combination is the key PleaseAI divergence from antfu’s defaults: control-flow statements must always use braces, but antfu’s top-level-function preference is still honoured.
Formatters
ESLint can’t natively format .css, .html, .xml, or Markdown frontmatter. Opt in to the formatters feature to delegate those files to eslint-plugin-format (which wraps Prettier / dprint) while keeping everything else on pure ESLint:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai({
formatters: {
css: true,
html: true,
markdown: 'prettier',
},
})bun add -D eslint-plugin-formatpnpm add -D eslint-plugin-formatnpm install -D eslint-plugin-formatType Aware Rules
The strongest TypeScript rules require type information. Opt in by pointing at your tsconfig.json:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai({
typescript: {
tsconfigPath: 'tsconfig.json',
},
})Read more in Advanced Usage → Type Aware Rules.
Next Steps
Framework Integrations
React, Next.js, Vue, Svelte, Astro, Solid, UnoCSS, and Angular — with peer deps.
Advanced Usage
Config Composer, command codemods, plugin renaming, versioning policy.
Editor & CI
VS Code, Neovim, editor-specific disables, and lint-staged.
Nuxt Integration
Compose with @nuxt/eslint for auto-import-aware linting.
FAQ
Prettier?
This config uses ESLint for both linting and formatting, so Prettier isn’t needed. See Why I don’t use Prettier by Anthony Fu for the reasoning.
If you need to format files ESLint can’t handle yet (.css, .html, etc.), use the formatters option — it wraps Prettier/dprint under the hood without adding a separate tool to your workflow.
How do I format CSS?
Opt in to the formatters feature. It formats but does not lint — for proper CSS linting pair it with Stylelint.
Curly braces style?
PleaseAI enforces curly: ['error', 'all'] — always wrap control-flow bodies in braces:
// ✓ required
function example() {
if (foo) {
return true
}
}
// ✗ rejected
function example() {
if (foo) return true
}This diverges from antfu’s default (which allows brace-less single-line if). We made this choice because brace-less bodies interact badly with our other rules like style/max-statements-per-line — mixing them produces hard-to-read one-liners.
Top-level function style?
PleaseAI re-enables antfu/top-level-function, so top-level functions should use a function declaration rather than an arrow assigned to a const:
// ✓ preferred
export function greet(name: string) {
return `Hello, ${name}`
}
// ✗ flagged
export const greet = (name: string) => `Hello, ${name}`Arrow functions are still fine inside function bodies, as callbacks, or for inline JSX handlers — the rule only targets top-level declarations. If you disagree, override it:
import pleaseai from '@pleaseai/eslint-config'
export default pleaseai({
rules: {
'antfu/top-level-function': 'off',
},
})