Decyzje dotyczące aktualizacji na TypeScript 7: Parallel Checkers, tryb obserwacji oraz luki w API
Jakie zmiany zachodzą przy przechodzeniu z TypeScript 6 na natywny dla Go TypeScript 7, jak działają nowe flagi paralelizmu oraz które zestawy narzędzi powinny poczekać z aktualizacją.
Źródła: TypeScript 7 vs TypeScript 6: What Actually Changed?
TypeScript 7 to nietypowa główna wersja: język, którym piszemy, pozostaje niezmieniony, natomiast program służący do jego sprawdzania i kompilowania został zastąpiony. Dla większości zespołów aktualizacja przynosi znaczne przyspieszenie bez konieczności naprawiania czegokolwiek, ale dla tych, których narzędzia komunikują się bezpośrednio z kompilatorem, może stanowić przeszkodę. Ten przewodnik wyjaśnia, czym dokładnie różnią się wersje 6 i 7, jak korzystać z nowych mechanizmów kontrolowania równoległości oraz jak zdecydować, czy nasz projekt powinien zostać zaktualizowany już teraz, czy poczekać na kolejną wersję.
Blog już szczegółowo omówił przyspieszenie uzyskane dzięki przeróbce na Go oraz dlaczego przeniesienie na Go uszkodziło narzędzia do sprawdzania kodu i narzędzia frameworków, więc tutaj skupiamy się na praktycznej decyzji dotyczącej aktualizacji.
Ten sam język, nowy silnik
W momencie pisania tego tekstu TypeScript 7.0 został wydany jako stabilna wersja (data publikacji: 8 lipca 2026 roku; sprawdź notatki wydawnicze w celu uzyskania aktualnego stanu). Jest to przepisanie kompilatora z TypeScript na Go – projekt, który Microsoft ogłosił w marcu 2025 roku pod kryptonimem Corsa. Nie jest to nowa wersja języka w zwykłym rozumieniu: nie pojawiła się nowa składnia, semantyka systemu typów ma pozostać niezmieniona, a istniejące pliki .ts nie powinny przestać działać. Twój kod pozostaje taki sam; zmienia się tylko mechanizm działający pod nim.
Dlaczego trzeba było przepisać kompilator
Aż do wersji TypeScript 6 kompilator był napisany w języku TypeScript i uruchamiany na silniku JavaScript, co w praktyce oznaczało jedną wątkową ścieżkę do sprawdzania typów. W dużych monorepoach występowały trzy powszechne problemy:
- Edytorzy potrzebowali tak dużo czasu na załadowanie projektu, że programiści nauczyli się czekać.
- Kontrole typów w CI trwały kilka minut na każdą rundę.
- Użycie pamięci było na tyle duże, że laptopy miały znaczne trudności z jej obsługą.
Zespół optymalizował implementację w JavaScriptie przez lata i doszedł do wniosku, że wąskim gardłem jest sam czas wykonywania, a nie algorytmy. Dlatego narzędzie kontrolne zostało przeniesione na Go, starając się zachować jego strukturę jak najbliżej istniejącego kodu. Ten wybór ma znaczenie: to wierny port, a nie przeprojektowanie, sprawia, że odchylenia w zachowaniu pozostają niewielkie.
Co różni się w praktyce
Znacznie szybsze kontrole typów
Opublikowane przez Microsoft wyniki testów pokazują skalę ulepszeń: sprawdzanie typów w kodzie VS Code skróciło się z 77,8 sekundy do 7,5 sekundy, czyli jest około dziesięć razy szybsze, natomiast Playwright przyspieszył z 11,1 sekundy do 1,1 sekundy. Dwa czynniki przyczyniły się do tego efektu. Kompilator teraz działa jako kod maszynowy natywny, zamiast JavaScriptu wykonywanego przez silnik, a także może sprawdzać elementy równolegle za pomocą gorutin, czego stary model jednowątkowy nigdy nie był w stanie osiągnąć. Wasze własne wyniki będą zależeć od struktury projektu; wiele małych, niezależnych plików daje lepsze efekty paralelizmu niż jeden ogromny, skomplikowany zbiór typów.
Nowe narzędzia w linii poleceń do zarządzania paralelizmem
Plik tsconfig.json nie ulega zmianie, ponieważ opisuje język i projekt, a nie sposób, w jaki kompilator planuje swoją pracę. Poniższa konfiguracja jest ważna dla obu wersji:
// tsconfig.json — nothing changes here, this is the language, not the compiler
{
"compilerOptions": {
"strict": true,
"target": "ES2022"
}
}
Nowe opcje znajdują się zamiast tego w linii poleceń. --checkers określa, ilu pracowników do spraw weryfikacji typów działa równolegle, --builders kontroluje, ilu procesów budowania odnośników do projektów może przebiegać jednocześnie, a --singleThreaded całkowicie wyłącza możliwość pracy równoległej:
# But at the CLI level, TypeScript 7 gives you real knobs to turn:
tsc --checkers 4 # number of parallel type-checker workers
tsc --builders 2 # parallel project-reference builds
tsc --singleThreaded # opt out entirely, useful for reproducible CI logs
Tryb jednowątkowy jest przydatny, gdy potrzebne są deterministyczne i łatwe do odczytania logi CI lub gdy próbuje się rozwiązać problem z kolejnością wykonywania operacji. Na współdzielonych maszynach do CI ograniczenie liczby --checkers do liczby dostępnych rdzeni zapobiega przeciążeniu urządzenia; więcej pracowników oznacza również większe zużycie pamięci jednocześnie, dlatego lepiej dokonać pomiarów zamiast ślepo dążyć do maksymalizacji.
Zmodyfikowany tryb obserwacji
W dużych projektach stary mechanizm obserwacji plików oparty na pytaniami stanowił znany problem – tsc --watch nie nadążał za zmianami. TypeScript 7 przenosi podejście do obserwacji plików używane przez mechanizm Parcel do języka Go, dzięki czemu ponowna kompilacja rozpoczyna się natychmiast po zapisaniu pliku, bez opóźnień.
Prostsze pakowanie
W okresie wstępnego testowania używanie lokalnego kompilatora wymagało instalacji oddzielnego pakietu @typescript/native-preview. W wersji 7.0 wszystko wróciło pod standardową nazwę pakietu, więc instalacja wygląda dokładnie tak jak zawsze:
npm install -D typescript
Jeśli eksperymentowałeś z wersją wstępną, usuń ten dodatkowy pakiet oraz wszystkie skrypty uruchamiające jego osobny plik binarny, aby nie mieć do czynienia z dwoma kompilatorami jednocześnie.
Prawdziwa luka: interfejs programistyczny
To jest ta część, która decyduje o wielu ulepszeniach. Narzędzia oparte na API kompilatora TypeScript, takie jak wtyczki language-service, niestandardowe reguły lintingu oraz codemody, nie mogą jeszcze polegać na stabilnym API programowym kompilatora Go w wersji 7.0; według obecnych przewidywań ma ono zostać dostarczone w późniejszej wersji, a jako cel wskazano wersję 7.1. Jeśli twoja ścieżka przetwarzania wykorzystuje coś w rodzaju ts.createProgram() do analizy programu, dokładnie sprawdź tę ścieżkę przed jej wdrożeniem w produkcji.
Rzeczywisty scenariusz migracji
Rozważmy średniej wielkości monorepo w Next.js zawierające około 40 000 linii kodu napisanego w TypeScript oraz kilka odniesień do projektów. Przejście na wersję 7.0 w takim setupie może skrócić czas wykonywania polecenia tsc --noEmit z około 52 sekund do około 6. Sześć sekund oszczędności przy jednym uruchomieniu wydaje się niewiele, ale dotyczy to każdego zadania w CI, każdego hooka przed zapisaniem zmian oraz każdej ręcznej weryfikacji podczas debugowania, a w skali całego zespołu daje to setki godzin oszczędności tygodniowo.
W przypadku projektów, które używają tylko tsc do weryfikacji i budowania, sama migracja zazwyczaj nie przynosi większych zmian: wystarczy zaktualizować pakiet, uruchomić narzędzie weryfikacyjne i upewnić się, że wszystko przejdzie bez konieczności zmian w kodzie.
npm install -D typescript@latest
npx tsc --noEmit # ran clean, zero code changes needed
Czyste uruchomienie jest oczekiwanym wynikiem, ale nie gwarancją. Zachowaj wynik z wersji TypeScript 6 do porównania i sprawdź zgłoszone błędy po pierwszym uruchomieniu, ponieważ w tak dużym projekcie zawsze mogą wystąpić specyficzne przypadki.
Czy powinieneś teraz dokonać aktualizacji?
- Zaktualizuj teraz, jeśli używasz
tscwyłącznie do sprawdzania typów i kompilacji. Jest to w praktyce prosta poprawka bez konieczności zmian. - Poczekaj lub rozdziel, jeśli polegasz na programowej API kompilatora poprzez własne narzędzia, wtyczki edytora lub moduły kodowe. Poczekaj na stabilną API albo utrzymuj zainstalowany TypeScript 6 dla tych narzędzi, używając jednocześnie wersji 7 do sprawdzania.
- Nadaj temu priorytet, jeśli zarządzasz bardzo dużym monorepo, gdzie czas wykonywania testów CI stanowi rzeczywisty koszt. Oszczędności czasu mogą zrekompensować wysiłek związany z migracją w ciągu kilku dni.
Główne wnioski
- TypeScript 7 zmienia kompilator, a nie język; pliki
tsconfig.jsonoraz źródłowe pliki pozostają bez zmian. - Szybsza praca wynika z wykorzystania kodu natywnego oraz równoległego sprawdzania, co można dostosować za pomocą parametrów
--checkers,--buildersi--singleThreaded.