Back

Guía de Migración ESLint 10: Todo sobre la actualización más grande

ESLint 10 acaba de salir, y no es una actualización menor. El sistema de configuración .eslintrc al que te aferrabas? Eliminado completamente—no deprecado, eliminado. El flag --env? Ya no existe. Node.js 18? Ya no soportado.

Esta es la declaración del equipo de ESLint: flat config es el único camino.

Si has pospuesto la migración, enero 2026 es tu deadline. ESLint 9 está en modo mantenimiento. ESLint 10 es el presente. Esta guía te llevará sin romper tu pipeline de CI.

Qué hay de nuevo en ESLint 10

Veamos qué cambió antes de meternos en la migración.

Node.js 20.19.0+ requerido

ESLint 10 deja de soportar Node.js 18, 19, 21 y 23. Necesitas:

  • Node.js ^20.19.0 (20.19.0 o superior en 20.x)
  • Node.js ^22.13.0 (22.13.0 o superior en 22.x LTS)
  • Node.js >=24.0.0 (24.x Current)

Revisa tus pipelines CI/CD. Esto romperá builds en versiones viejas de Node inmediatamente.

node --version # Debe ser v20.19.0+

Eliminación completa de .eslintrc

Este es el grande. ESLint 10 elimina todo relacionado con la configuración legacy:

EliminadoReemplazo
Archivos .eslintrc.*eslint.config.js
.eslintignoreArray ignores en config
Flag --envglobals en languageOptions
Flag --rulesdirImports directos de plugins
--resolve-plugins-relative-toImports de módulos ES
Comentarios /* eslint-env */Ahora reportados como errores
Variable env ESLINT_USE_FLAT_CONFIGSiempre flat config
API LegacyESLintEliminada totalmente

Si tu proyecto todavía usa .eslintrc.json, ESLint 10 simplemente lo ignorará.

Nuevo lookup de archivos de configuración

ESLint 10 cambia cómo encuentra archivos de config:

ESLint 9 (comportamiento viejo):

Buscar desde CWD hacia arriba por eslint.config.js

ESLint 10 (comportamiento nuevo):

Buscar desde el directorio de cada archivo linteado hacia arriba por eslint.config.js

Esto es enorme para monorepos. Cada paquete puede tener su propio eslint.config.js, y ESLint lo encontrará automáticamente.

my-monorepo/
├── eslint.config.js          # Config raíz (fallback)
├── packages/
│   ├── web/
│   │   ├── eslint.config.js  # Config específica web
│   │   └── src/
│   └── api/
│       ├── eslint.config.js  # Config específica API
│       └── src/

Tracking de referencias JSX

ESLint 10 ahora trackea referencias de elementos JSX para análisis de scope preciso:

  • Componentes custom son trackeados apropiadamente como referencias
  • no-unused-vars funciona correctamente con JSX
  • Código existente podría disparar nuevas advertencias (false positives en v9)
// ESLint 10 ahora ve Button correctamente como referencia import { Button } from './components'; function App() { return <Button>Click me</Button>; // Button es trackeado }

eslint:recommended actualizado

El ruleset recomendado ha sido actualizado. Corre ESLint después de migrar para atrapar nuevas violaciones.

Migración paso a paso desde ESLint 9

Paso 1: Verifica versión de Node.js

node --version # Si es menor a v20.19.0, actualiza primero

Actualiza tu CI/CD para usar Node.js 20.x LTS o 22.x.

Paso 2: Actualiza ESLint y dependencias

npm install eslint@10 --save-dev # Actualiza TypeScript ESLint si usas TypeScript npm install @typescript-eslint/eslint-plugin@latest @typescript-eslint/parser@latest --save-dev # Actualiza otros plugins npm install eslint-plugin-react@latest eslint-plugin-react-hooks@latest --save-dev

Paso 3: Migra la config (si no lo has hecho)

Si todavía estás en .eslintrc, usa la herramienta de migración:

npx @eslint/migrate-config .eslintrc.json

Esto genera un archivo eslint.config.mjs. Revísalo y ajústalo.

Paso 4: Actualiza tu Flat Config para compatibilidad v10

Si ya tienes eslint.config.js, verifica estas actualizaciones específicas de v10:

Elimina comentarios eslint-env

// ❌ ESLint 10 reporta esto como error /* eslint-env browser, node */ // ✅ Usa globals en config en su lugar import globals from "globals"; export default [ { languageOptions: { globals: { ...globals.browser, ...globals.node, } } } ];

Paso 5: Elimina archivos legacy

rm .eslintrc.* .eslintignore 2>/dev/null || true

Paso 6: Actualiza configuración de VS Code

{ "eslint.useFlatConfig": true }

Nota: La configuración eslint.useFlatConfig ahora es el default. Puedes eliminarla.

Paso 7: Prueba

npx eslint .

Corrige nuevas violaciones del eslint:recommended actualizado o cambios en tracking JSX.

Ejemplos completos de config ESLint 10

Proyecto TypeScript

// eslint.config.js import js from "@eslint/js"; import typescript from "typescript-eslint"; import globals from "globals"; export default typescript.config( js.configs.recommended, ...typescript.configs.recommendedTypeChecked, { languageOptions: { globals: globals.node, parserOptions: { projectService: true, tsconfigRootDir: import.meta.dirname, }, }, }, { files: ["**/*.js", "**/*.mjs"], ...typescript.configs.disableTypeChecked, }, { ignores: ["dist/**", "node_modules/**"], } );

React + TypeScript (Next.js)

// eslint.config.mjs import js from "@eslint/js"; import typescript from "typescript-eslint"; import react from "eslint-plugin-react"; import reactHooks from "eslint-plugin-react-hooks"; import jsxA11y from "eslint-plugin-jsx-a11y"; import next from "@next/eslint-plugin-next"; import globals from "globals"; export default typescript.config( js.configs.recommended, ...typescript.configs.recommended, // React + JSX { files: ["**/*.{jsx,tsx}"], plugins: { react, "react-hooks": reactHooks, "jsx-a11y": jsxA11y, }, languageOptions: { globals: globals.browser, parserOptions: { ecmaFeatures: { jsx: true }, }, }, settings: { react: { version: "detect" }, }, rules: { ...react.configs.recommended.rules, ...react.configs["jsx-runtime"].rules, ...reactHooks.configs.recommended.rules, ...jsxA11y.configs.recommended.rules, }, }, // Next.js { plugins: { "@next/next": next, }, rules: { ...next.configs.recommended.rules, ...next.configs["core-web-vitals"].rules, }, }, { ignores: [".next/**", "node_modules/**", "out/**"], } );

Monorepo con configs por paquete

// Raíz: eslint.config.js import js from "@eslint/js"; import typescript from "typescript-eslint"; // Config base que todos los paquetes heredan export default typescript.config( js.configs.recommended, ...typescript.configs.recommended, { ignores: ["**/dist/**", "**/node_modules/**"], } );
// packages/web/eslint.config.js import baseConfig from "../../eslint.config.js"; import react from "eslint-plugin-react"; import globals from "globals"; export default [ ...baseConfig, { files: ["**/*.{jsx,tsx}"], plugins: { react }, languageOptions: { globals: globals.browser, }, rules: { ...react.configs.recommended.rules, }, }, ];

El nuevo algoritmo de lookup de ESLint 10 usará automáticamente el eslint.config.js más cercano a cada archivo.

Errores comunes de migración y soluciones

Error: "ESLint requires Node.js version ^20.19.0 || ^22.0.0 || >=24.0.0"

Solución: Actualiza Node.js a 20.19.0 o superior.

# Usando nvm nvm install 22 nvm use 22

Error: "eslint-env is no longer supported"

Solución: Elimina comentarios /* eslint-env */ y usa globals:

import globals from "globals"; { languageOptions: { globals: globals.browser } }

Error: "ConfigArray.normalize is not a function"

Solución: Actualiza @eslint/eslintrc a la última versión:

npm install @eslint/eslintrc@latest

Error: "Cannot find config" en monorepo

Solución: ESLint 10 busca desde el directorio del archivo, no CWD. Opciones:

  1. Agrega eslint.config.js a cada paquete, o
  2. Corre ESLint desde la raíz con patrones de archivo explícitos

Warning: Nuevas violaciones del tracking JSX

Solución: Probablemente son problemas reales que v9 no detectó. Revisa cada uno. Si es false positive, deshabilita la regla para esa línea.

Checklist de migración

Usa este checklist para tu migración:

  • Node.js es v20.19.0+ o v22.x
  • ESLint actualizado a v10
  • Todos los plugins actualizados a versiones compatibles con v10
  • Config migrada a eslint.config.js
  • Todos los comentarios /* eslint-env */ eliminados
  • Archivos .eslintrc.* eliminados
  • .eslintignore eliminado (usa ignores en config)
  • CI/CD actualizado a Node.js 20+
  • Configuración de VS Code actualizada
  • Lint completo pasa

¿Deberías migrar ahora?

Sí. Razones:

  1. ESLint 9 está en modo mantenimiento—sin nuevas features, solo fixes críticos
  2. Ecosistema de plugins se está moviendo—plugins populares están dejando de soportar v9
  3. El nuevo algoritmo de lookup es poderoso—especialmente para monorepos
  4. Tracking JSX encuentra bugs reales—tu código existente podría tener problemas que no conocías

La migración es mayormente mecánica. Si ya te moviste a flat config en v9, estás 90% listo. Si todavía estás en .eslintrc, ahora es el momento—no hay más tiempo.

Conclusión

ESLint 10 es un quiebre limpio con el pasado. El sistema de configuración legacy se fue para siempre. Lo que obtienes a cambio:

  • Modelo mental más simple: Un archivo, un formato, sin magia
  • Mejor soporte monorepo: Configs por paquete que simplemente funcionan
  • Linting más preciso: Tracking JSX encuentra problemas reales
  • Preparado para el futuro: Estás en el camino que toma el ecosistema

La migración puede tomar una hora o dos, pero estarás listo para los próximos años de releases de ESLint.

Una deuda técnica menos. ¡Ahora ve a actualizar esas configs! 🚀

ESLintJavaScriptTypeScriptLintingMigrationDeveloper Tools

Explora herramientas relacionadas

Prueba estas herramientas gratuitas de Pockit