# Oxlint vs ESLint: qual linter de JS para CI?

> Oxlint vs ESLint no CI: linting na velocidade do Rust vs o ecossistema completo de regras, cobertura e uso complementar. Qual linter de JavaScript mantém o lint de CI rápido.

Source: https://latchkey.dev/pt/learn/tool-comparisons/oxlint-vs-eslint  
Updated: 2026-08-20

O Oxlint (do projeto Oxc) é um linter baseado em Rust que roda ordens de magnitude mais rápido que o ESLint, que mantém o ecossistema completo de regras e plugins.

O ESLint é o linter padrão de JavaScript/TypeScript com o maior conjunto de regras e plugins. O Oxlint é um linter baseado em Rust focado em velocidade, cobrindo muitas regras comuns com configuração quase nula e melhorando a cobertura com o tempo.

## Comparison

|  | Oxlint | ESLint |
| --- | --- | --- |
| Implementação | Rust | JavaScript |
| Velocidade | Extremamente rápida | Mais lenta |
| Cobertura de regras | Muitas regras comuns, em crescimento | Completa, a maior |
| Ecossistema de plugins | Limitado, em crescimento | O maior |
| Config | Quase zero | Flexível |
| Lint com reconhecimento de tipos | Sim, via tsgo (TypeScript 7) | Sim, via typescript-eslint |
| Formato de configuração | Configuração própria, no estilo ESLint | Flat config (`eslint.config.js`) na v9 e v10 |
| Autofix | Sim (`--fix`) | Sim (`--fix`) |
| Integração com editor | Disponível | Universal |
| Substituto drop-in | Ainda não | n/a |

## No CI

O Oxlint pode fazer lint de bases de código enormes em uma fração do tempo do ESLint, o que o torna atraente como um gate rápido de primeira passagem. Ele ainda não cobre todas as regras ou plugins do ESLint, então muitas equipes rodam o Oxlint para velocidade e mantêm o ESLint para as regras que faltam ao Oxlint - frequentemente o Oxlint a cada push e uma passagem mais completa do ESLint com menos frequência. Se você depende de plugins custom ou específicos de framework, o ESLint continua essencial.

| ESLint lint step | Oxlint at 50x | Oxlint at 100x |
| --- | --- | --- |
| 10 seconds | 0.2 s | 0.1 s |
| 60 seconds | 1.2 s | 0.6 s |
| 3 minutes | 3.6 s | 1.8 s |
| 8 minutes (large monorepo) | 9.6 s | 4.8 s |

> The second-order effect matters more than the runner minutes. A lint step that finishes in under two seconds can run as a pre-commit hook and on every keystroke in the editor, which moves lint failures out of CI entirely. An eight-minute lint step can only ever run in CI, where it blocks a merge.

## Use-os juntos

Rode o Oxlint como um pré-check rápido e o ESLint para as regras que ele não cobre; não precisa cachear nada especial, já que o linting é limitado por CPU. Ambos rodam em managed runners; runners gerenciados mais rápidos encurtam a passagem do ESLint em repos grandes.

- What ports cleanly: core correctness rules, TypeScript rules, React hooks and JSX rules, and the common test-framework plugins.
- What does not: your own in-house rules, and smaller community plugins nobody has ported.
- Rule *names* mostly match ESLint, so disable comments and config intent carry over more easily than a rewrite would suggest.

> Audit before you plan. List the plugins in your config, then check each against the oxlint rule list. That single exercise tells you whether you are looking at a migration or a supplement, and it takes about twenty minutes.

## O lint com reconhecimento de tipos é a mudança mais nova e maior

Regras com reconhecimento de tipos são as que precisam do type checker e não apenas da árvore sintática: promises soltas, propagação insegura de `any`, promises mal usadas. Historicamente eram exclusivas do ESLint via typescript-eslint, e também eram as regras mais lentas de qualquer configuração porque exigem uma verificação de tipos completa.

- O oxlint agora suporta lint com reconhecimento de tipos integrando-se ao port em Go do TypeScript (tsgo, TypeScript 7), habilitando verificações como detecção de promises soltas.
- Isso remove o que era a razão técnica mais forte para uma base TypeScript não poder sequer considerar o oxlint.
- É também a área que se move mais rápido, então verifique a cobertura atual contra as regras das quais você realmente depende em vez de presumir paridade.

## O bloqueio real: plugins customizados estão em alfa

Se você mantém regras internas, é isso que decide tudo. O oxlint suporta plugins JS compatíveis com o ecossistema de plugins do ESLint, mas esse suporte está documentado como alfa. Alfa serve para um experimento de lint e não serve para o portão que bloqueia os seus merges.

- Um repositório sem regras customizadas e com plugins mainstream muitas vezes já pode migrar hoje.
- Um repositório com regras internas que codificam restrições arquiteturais deve manter o ESLint especificamente para essas regras.
- Plugins nativos (Rust) são estáveis, mas significam escrever Rust, o que é uma proposta diferente de manter uma regra em JS.

## O padrão que repositórios grandes de fato usam: os dois

Em vez de escolher, rode o oxlint como um pré-filtro rápido e o ESLint para as regras que o oxlint ainda não cobre. Você ganha o ciclo rápido de feedback onde importa e mantém a cobertura completa onde precisa.

```Running both, fast pass first
# package.json scripts
{
  "scripts": {
    "lint:fast": "oxlint",
    "lint:full": "eslint .",
    "lint": "oxlint && eslint ."
  }
}

# .github/workflows/ci.yml
jobs:
  lint:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-node@v4
        with: { node-version: 22, cache: npm }
      - run: npm ci
      # Fails in about a second on the 865 rules oxlint covers,
      # so the slow full pass only runs on code that already passes.
      - run: npx oxlint
      - run: npx eslint .
```

> A ordem importa. Colocar o oxlint primeiro faz a esmagadora maioria das falhas de lint aparecer em cerca de um segundo, e a passagem lenta do ESLint só roda sobre código que já passou pela rápida. Isso é uma latência de falha estritamente melhor que o ESLint sozinho, sem perda de cobertura.

## Quando uma migração completa faz sentido

1. Faça o inventário dos seus plugins do ESLint e regras customizadas, e confira cada um contra a lista de regras do oxlint.
2. Se nada customizado aparecer, rode `oxlint` ao lado do ESLint no CI por algumas semanas e compare os achados.
3. Investigue cada discordância. Regras com o mesmo nome podem divergir nas bordas, e é nessas bordas que uma mudança silenciosa de comportamento se esconde.
4. Mova a passagem rápida para um hook de pre-commit quando confiar nela, para que falhas de lint parem de chegar ao CI.
5. Aposente o ESLint apenas quando o diff estiver vazio e nada na sua configuração depender do suporte alfa a plugins JS.

## The switching cost is mostly in the parts nobody lists

- Assertions and mocks usually port mechanically when the target implements a compatible API; custom transformers and framework plugins do not.
- Snapshot formats differ between runners, so plan to regenerate and review rather than port.
- Run both suites in parallel in CI for a period and diff the results. A migration that changes which tests fail is not a migration, it is a regression you have not found yet.
- Coverage numbers move on a runner change even when the tests do not, because instrumentation differs. Re-baseline any coverage gate deliberately.

## O veredito

Quer uma passagem de lint ultrarrápida e suas regras críticas estão cobertas: Oxlint (frequentemente ao lado do ESLint). Precisa do ecossistema completo de regras e plugins: ESLint. Muitas equipes os combinam - Oxlint para velocidade, ESLint para cobertura.

## FAQ

### O oxlint é um substituto drop-in do ESLint?

Ainda não. Ele cobre mais de 865 regras e os nomes das regras coincidem em grande parte com os do ESLint, então configurações mainstream portam bem. O bloqueio é que o suporte a plugins JS, do qual dependem regras customizadas e de nicho, ainda é alfa. Repositórios sem regras internas costumam poder migrar; os que têm devem manter o ESLint para essas regras.

### Quanto o oxlint é mais rápido que o ESLint?

O benchmark publicado é de 50 a 100 vezes mais rápido. Na prática isso transforma um passo de lint de 60 segundos em cerca de um segundo, e um lint de monorepo de oito minutos em menos de dez segundos. O efeito maior é qualitativo: um lint de menos de um segundo pode rodar a cada save e como hook de pre-commit, então falhas param de chegar ao CI.

### O oxlint suporta lint com reconhecimento de tipos?

Sim, pela integração com o port em Go do TypeScript (tsgo, TypeScript 7), que habilita verificações como detecção de promises soltas. Isso é recente e avança rápido, então verifique a cobertura das regras específicas de que você depende em vez de presumir paridade total com o typescript-eslint.

### Quantas regras o oxlint tem?

Mais de 865, abrangendo regras core do ESLint, regras de TypeScript e conjuntos de regras de plugins populares, incluindo React, Jest e Vitest.

### Posso rodar oxlint e ESLint juntos?

Sim, e é o padrão recomendado. Rode `oxlint` primeiro para que a maioria das violações apareça em cerca de um segundo, e depois `eslint .` para as regras que o oxlint não cobre. A latência de falha melhora sem perda de cobertura.

### Quem usa oxlint em produção?

Elastic Kibana, Sentry e Cloudflare são adotantes citados. Note que são bases de código grandes, o caso em que a diferença de velocidade mais se acumula e em que uma passagem completa do ESLint é mais dolorosa.

### O oxlint suporta autofix?

Sim, via `oxlint --fix`, no mesmo formato de `eslint --fix`. Por ser muito mais rápido, o autofix ao salvar é prático de um jeito que uma passagem lenta do ESLint frequentemente não é.

### Meus comentários de disable do ESLint continuam funcionando?

Em grande parte, porque o oxlint deliberadamente espelha os nomes de regras do ESLint. Dito isso, regras com o mesmo nome podem divergir nas bordas, então rode os dois em paralelo por um período e compare os achados antes de aposentar qualquer coisa.

---

Latchkey runs CI/CD that repairs its own failures. Agent entry points: https://latchkey.dev/agent.txt, https://latchkey.dev/openapi.json, https://latchkey.dev/llms.txt
