Przejdź do treści
Biome

Biome zamiast ESLint i Prettier — jak przeprowadzić migrację i odzyskać czas w CI

Lintowanie i formatowanie kodu to jeden z tych obszarów, gdzie każdy zespół kiedyś traci czas, który mógłby poświęcić na właściwą pracę. ESLint konfiguruje się przez godziny. Prettier kłóci się z ESLint przez eslint-config-prettier. Pre-commit hooki trwają osiem sekund. CI blokuje PR przez minuty.

10 хв читанняREL8

Lintowanie i formatowanie kodu to jeden z tych obszarów, gdzie każdy zespół kiedyś traci czas, który mógłby poświęcić na właściwą pracę. ESLint konfiguruje się przez godziny. Prettier kłóci się z ESLint przez eslint-config-prettier. Pre-commit hooki trwają osiem sekund. CI blokuje PR przez minuty. I każdy nowy developer musi rozgryźć, dlaczego w projekcie jest siedem różnych plików konfiguracyjnych.

Biome to odpowiedź na ten problem — jeden plik konfiguracyjny, jedna komenda, prędkość liczona w milisekundach. W tym artykule pokazuję, jak przeprowadzić migrację w istniejącym projekcie TypeScript, na co uważać i co konkretnie możesz zyskać.


Dlaczego ESLint + Prettier staje się problemem

Na początku projektu konfiguracja ESLint i Prettier wydaje się prosta. Instalujesz kilka pakietów, kopiujesz config z poprzedniego projektu i działa. Problem zaczyna się, gdy projekt rośnie.

Typowy package.json po roku wytwarzania kodu wygląda tak: eslint, prettier, eslint-config-prettier, eslint-plugin-react, eslint-plugin-import, @typescript-eslint/eslint-plugin, @typescript-eslint/parser, eslint-plugin-jsx-a11y, eslint-plugin-unicorn — i to nie jest kompletna lista. Każdy z tych pakietów ma własne zależności, własny cykl wydań i własny sposób konfiguracji. Gdy wychodzi nowa wersja TypeScript albo React, przez kilka tygodni czekasz, aż wszystkie pluginy ją obsłużą.

Drugi problem to prędkość. ESLint działa w jednym wątku i nie był projektowany z myślą o dużych monorepo. W kodzie z realnej produkcji lintowanie 200,000 linii kodu bez automatycznych poprawek zajmowało prawie siedem minut. Pre-commit hooki trwające powyżej pięciu sekund to efektywnie hooki, które developerzy wyłączają — bo nikt nie będzie czekał osiem sekund przy każdym commicie.

Trzeci problem to konfiguracja. Masz .eslintrc.json, .eslintignore, .prettierrc, .prettierignore. Jeśli pracujesz w monorepo, tych plików jest kilkanaście. Onboarding nowego developera to nie tylko npm install — to półgodzinna rozmowa o tym, dlaczego konfiguracja wygląda tak jak wygląda.


Czym jest Biome i co oferuje

Biome to toolchain do analizy i formatowania kodu, napisany w Rust. Łączy formatter (zamiennik Prettier) i linter (zamiennik ESLint) w jednym binarnym pliku, z jedną konfiguracją w biome.json.

Projekt zaczął się jako fork porzuconego Rome Tools. Od 2023 roku działa jako niezależny projekt. Wersja 1.0 pojawiła się w sierpniu 2023, wersja 2.0 w 2025, a aktualna — 2.4 — pochodzi z początku 2026. Na GitHubie projekt ma ponad 24 tysiące gwiazdek i wygrał nagrodę "Productivity Booster" na OS Awards 2024.

Co Biome robi lepiej niż ESLint+Prettier:

Prędkość. Biome jest napisany w Rust, działa wielowątkowo i nie wczytuje setek modułów Node.js przy każdym uruchomieniu. Oficjalny benchmark: 171,000 linii kodu w ponad 2,000 plikach — Biome jest ~35x szybszy od Prettier przy formatowaniu. W praktyce, na monorepo z prawdziwego projektu, lintowanie z automatycznym naprawianiem błędów skrócono z 7 minut do 1.6 sekundy. To 250-krotne przyspieszenie.

Jeden plik konfiguracyjny. Zamiast pięciu plików masz biome.json. Formatter, linter, organizacja importów — wszystko w jednym miejscu.

Kompatybilność z Prettier. Biome osiąga 97% kompatybilności z Prettier (mierzone na rzeczywistym kodzie open source). Różnice są, ale są udokumentowane i w większości pomijalne dla przeciętnego projektu.

Linter z 467 regułami. Biome pokrywa reguły z @typescript-eslint, eslint-plugin-react, eslint-plugin-jsx-a11y i eslint-plugin-unicorn. Nie jest to 100% pokrycie, ale dla większości projektów wystarczy.

Od wersji 2.0 Biome oferuje też system pluginów (GritQL), który pozwala pisać własne reguły lintowania — to odpowiedź na jeden z głównych argumentów za pozostaniem przy ESLint.

Co Biome formatuje: JavaScript, TypeScript, JSX, TSX, JSON, JSONC, CSS, GraphQL, HTML (eksperymentalnie).

Czego Biome jeszcze nie robi: SCSS, Markdown, pełne wsparcie dla plików Astro/Vue/Svelte z embedded languages.


Jak przeprowadzić migrację — krok po kroku

Migracja w większości projektów zajmuje od jednej do kilku godzin. Poniżej konkretne komendy.

Krok 1: Instalacja


npm install --save-dev --save-exact @biomejs/biome

Flaga --save-exact przypina konkretną wersję Biome. Oficjalna dokumentacja to zaleca, żeby wszyscy w zespole pracowali na tej samej wersji formattera — różne wersje mogą produkować różny output, co powoduje fałszywe diffe w PR.

Krok 2: Inicjalizacja konfiguracji


npx @biomejs/biome init

Tworzy biome.json z domyślną konfiguracją. Na tym etapie masz działające narzędzie — możesz już uruchomić npx biome check . i zobaczyć, co Biome wykrywa w Twoim kodzie.

Krok 3: Migracja z ESLint


npx @biomejs/biome migrate eslint --write

Biome czyta Twój plik .eslintrc.js lub eslint.config.js, obsługuje sekcje extends, overrides i .eslintignore, i przenosi to wszystko do biome.json. Do załadowania pluginów ESLint potrzebuje Node.js, więc musi być zainstalowany razem z zależnościami projektu.

Krok 4: Migracja z Prettier


npx @biomejs/biome migrate prettier --write

Czyta .prettierrc lub prettier.config.js i przenosi ustawienia (styl wcięć, rodzaj cudzysłowów, trailing commas, szerokość linii) do sekcji formattera w biome.json.

Krok 5: Aktualizacja skryptów w package.json


{
  "scripts": {
    "lint": "biome lint .",
    "format": "biome format --write .",
    "check": "biome check --write .",
    "ci": "biome ci ."
  }
}

Warto znać różnicę między biome check a biome ci. Polecenie biome check łączy formatowanie, lintowanie i organizację importów — uruchamiaj je na maszynach developerskich z flagą --write, żeby automatycznie naprawiało błędy. Polecenie biome ci jest przeznaczone dla pipeline'ów — nie modyfikuje plików, tylko raportuje błędy. W GitHub Actions wyświetla je jako adnotacje bezpośrednio przy konkretnych liniach kodu.

Krok 6: Usunięcie starych narzędzi


npm uninstall eslint prettier eslint-config-prettier eslint-plugin-react \
  eslint-plugin-import @typescript-eslint/eslint-plugin @typescript-eslint/parser \
  eslint-plugin-jsx-a11y eslint-plugin-unicorn

Następnie usuń pliki konfiguracyjne: .eslintrc.js, .eslintignore, .prettierrc, .prettierignore. Po ich usunięciu środowisko jest czystsze i nie ma ryzyka, że stara konfiguracja będzie kolidować z nową.

Krok 7: Weryfikacja


npx @biomejs/biome check .

Przejrzyj wyniki i zdecyduj, które ostrzeżenia są akcjonowalne, a które chcesz wyłączyć w konfiguracji.

Diagram przepływu migracji
1
Diagram przepływu migracji: instalacja Biome
2
migrate eslint
3
migrate prettier
4
update package.json scripts
5
uninstall old tools
6
verify

Przykład biome.json dla projektu TypeScript

Minimalna konfiguracja, od której warto zacząć:


{
  "$schema": "https://biomejs.dev/schemas/2.4.0/schema.json",
  "vcs": {
    "enabled": true,
    "clientKind": "git",
    "useIgnoreFile": true
  },
  "files": {
    "ignoreUnknown": false,
    "ignore": ["dist/**", "node_modules/**", "coverage/**"]
  },
  "formatter": {
    "enabled": true,
    "indentStyle": "space",
    "indentWidth": 2,
    "lineWidth": 100
  },
  "organizeImports": {
    "enabled": true
  },
  "linter": {
    "enabled": true,
    "rules": {
      "recommended": true
    }
  },
  "javascript": {
    "formatter": {
      "quoteStyle": "single",
      "trailingCommas": "es5",
      "semicolons": "always"
    }
  }
}

Klucz "vcs" z "useIgnoreFile": true sprawia, że Biome honoruje wpisy z .gitignore. Nie musisz powielać listy ignorowanych ścieżek w dwóch miejscach.

Jeśli pracujesz z NestJS lub projektem opartym o dependency injection, dodaj dostosowanie dla reguły useImportType:


{
  "linter": {
    "rules": {
      "recommended": true,
      "style": {
        "useImportType": "off"
      }
    }
  }
}

Biome domyślnie konwertuje import { TagService } from './tag.service' na import type { TagService } from './tag.service'. W normalnym kodzie TypeScript to dobra praktyka. W NestJS psuje dependency injection, bo runtime nie widzi wartości — tylko typ. Lepiej wyłączyć tę regułę globalnie niż dodawać komentarze // biome-ignore w każdym serwisie.


Znane ograniczenia i gotchas

Biome to dojrzałe narzędzie, ale nie jest idealne. Uczciwa lista rzeczy, na które trafisz:

Pierwsze uruchomienie formattera zmienia tysiące linii. Mimo 97% kompatybilności z Prettier, różnice w trailing commas, cudzysłowach czy bracket spacing mogą wygenerować ogromny diff przy pierwszym biome format --write. To nie jest błąd — to jednorazowy koszt. Zrób to jako osobny commit z opisem chore: apply Biome formatting, żeby historia repozytorium była czytelna i żeby git blame pozostał użyteczny.

Brak reguł type-aware. Reguły wymagające informacji o typach TypeScript — jak @typescript-eslint/no-floating-promises czy @typescript-eslint/no-misused-promises — nie są jeszcze w pełni dostępne. Biome pracuje nad tym od wersji 2.0 (multi-file analysis), ale na dziś to luka. Jeśli te reguły są dla Ciebie krytyczne, możesz uruchamiać tsc --noEmit jako osobny krok w CI zamiast polegać na lintrze.

Brak wsparcia dla SCSS. Jeśli projekt używa SCSS, Biome go pominie. Stylelint pozostaje potrzebny dla SCSS — ale przynajmniej możesz go ograniczyć tylko do stylowania i nie mieszać z lintowaniem logiki.

Reguła noForEach może być irytująca. Biome zaleca zastępowanie .forEach() pętlą for...of. Dla wielu zespołów to zbyt opiniotwórcze. Wyłącz ją w konfiguracji:


"complexity": {
  "noForEach": "off"
}

WebStorm plugin jest mniej stabilny niż VS Code. Na początku 2026 pojawiły się raporty o crashach pluginu JetBrains. VS Code extension (biomejs.biome) działa bez problemów.

Migracja dużych projektów wymaga stopniowego podejścia. Oficjalny przewodnik zaleca, żeby przy dużym monorepo zacząć od włączenia samego formattera, a linter uruchamiać z --diagnostic-level=error, żeby na start widzieć tylko błędy krytyczne, nie wszystkie ostrzeżenia.


Integracja z VS Code i CI/CD

VS Code

Zainstaluj rozszerzenie biomejs.biome z Visual Studio Code Marketplace. Następnie zaktualizuj settings.json workspace:


{
  "editor.defaultFormatter": "biomejs.biome",
  "editor.formatOnSave": true,
  "editor.codeActionsOnSave": {
    "quickfix.biome": "explicit",
    "source.organizeImports.biome": "explicit"
  },
  "[javascript]": { "editor.defaultFormatter": "biomejs.biome" },
  "[typescript]": { "editor.defaultFormatter": "biomejs.biome" },
  "[json]": { "editor.defaultFormatter": "biomejs.biome" }
}

Po migracji wyłącz (lub odinstaluj) rozszerzenia ESLint i Prettier dla tego workspace. Jeśli zostawisz je aktywne, mogą produkować konfliktujące sugestie.

GitHub Actions

Biome ma oficjalny action, który automatycznie wykrywa wersję z package.json lub z pola $schema w biome.json:


name: Code quality

on:
  push:
  pull_request:

jobs:
  quality:
    runs-on: ubuntu-latest
    permissions:
      contents: read
    steps:
      - uses: actions/checkout@v5
        with:
          persist-credentials: false

      - name: Setup Biome
        uses: biomejs/setup-biome@v2
        with:
          version: latest

      - name: Run Biome
        run: biome ci .

Komenda biome ci w GitHub Actions wyświetla błędy jako adnotacje bezpośrednio przy konkretnych liniach kodu w interfejsie PR. Nie musisz przeglądać logów — błędy widać od razu przy przeglądaniu zmian.

Jeśli Twój biome.json używa extends z zewnętrznego pakietu, dodaj przed krokiem Setup Biome instalację zależności (npm ci), żeby Biome mógł załadować pakiet.

Podgląd wizualny
Screenshot
Widok GitHub Actions z adnotacjami Biome bezpośrednio przy liniach kodu w diff PR
Live preview
Widok GitHub Actions z adnotacjami Biome bezpośrednio przy liniach kodu w diff PR

Widok GitHub Actions z adnotacjami Biome bezpośrednio przy liniach kodu w diff PR


Co możesz wdrożyć już dziś

Migracja nie musi być zdarzeniem "all-or-nothing". Możesz zacząć małymi krokami:

Dzisiaj — 15 minut:

Zainstaluj Biome w jednym projekcie lub pakiecie, uruchom npx biome check . i przejrzyj wyniki. Nie musisz niczego zmieniać — po prostu sprawdź, co Biome wykrywa w porównaniu do aktualnego ESLint.

W tym tygodniu — 1–2 godziny:

Przeprowadź pełną migrację w projekcie, który ma prostą konfigurację ESLint (bez niestandardowych pluginów firmowych). Użyj komend biome migrate eslint i biome migrate prettier. Zrób commit z formatowaniem jako osobną zmianę.

W tym miesiącu:

Skonfiguruj biome ci w GitHub Actions lub GitLab CI. Zaaktualizuj VS Code settings dla całego zespołu (wrzuć .vscode/settings.json do repozytorium). Usuń stare pakiety z package.json.

Dla monorepo:

Zastąp husky + lint-staged jedną komendą biome check --staged . jako pre-commit hook. Możesz też użyć lefthook zamiast husky — jest szybszy i Biome świetnie z nim współpracuje.

Jeśli projekt używa NestJS, Angular lub innego frameworku z dependency injection, pamiętaj o wyłączeniu reguły useImportType przed pierwszym uruchomieniem biome check --write.


Ile możesz na tym zyskać

Liczby z produkcyjnych migracji, nie marketingowych prezentacji:

Czas lintowania: Monorepo z ~200,000 linii kodu — z 7 minut do 1.6 sekundy. To ~250-krotne przyspieszenie. Na mniejszych projektach skala jest mniejsza: projekt z 45 plikami Next.js schodzi z 3.2 sekundy do 0.4 sekundy (8x szybciej), projekt z 180 plikami — z 12.8 do 1.1 sekundy (11.6x szybciej).

Czas CI miesięcznie: Jeden z projektów po migracji zaoszczędził ponad 1,000 minut CI miesięcznie. Przy typowych cenach runners w GitHub Actions (ok. $0.008/minutę) to kilkaset złotych oszczędności — ale ważniejsze jest to, że PR przechodzą szybciej i developerzy nie czekają na feedback.

Pre-commit hooki: Z 8 sekund do praktycznie natychmiastowych. Hooki, które działają błyskawicznie, są faktycznie używane — i faktycznie łapią błędy przed commitem.

Liczba pakietów: Typowa migracja usuwa 8–12 pakietów npm z package.json. Mniej zależności to mniejsze node_modules, szybszy npm install i mniej podatności do śledzenia.

Onboarding: Nowy developer widzi jeden plik biome.json zamiast czterech różnych plików konfiguracyjnych. Nie musi rozumieć, dlaczego eslint-config-prettier wyłącza reguły ESLint, żeby nie kolidowały z Prettier — bo tego problemu po prostu nie ma.

Biome nie jest odpowiedzią na każdy problem z jakością kodu. Jeśli intensywnie korzystasz z type-aware rules z @typescript-eslint, SCSS, lub masz firmowe pluginy ESLint bez odpowiednika — migracja wymaga dodatkowego planowania. Ale dla większości projektów TypeScript/JavaScript, które używają standardowego zestawu reguł, Biome jest gotowy do produkcji i przynosi realne oszczędności od pierwszego dnia.

Якщо стаття була корисною, поділіться →

BiomeESLintPrettierJavaScriptTypeScriptnarzędzia deweloperskiemigracja ESLint Prettier BiomeBiome JavaScript TypeScriptbiome.json konfiguracjaESLint alternatywa

Схожі статті

Хочете впровадити AI у своїй компанії?

Замовте безкоштовну консультацію — визначимо, які процеси варто автоматизувати.