Vergleich der zwei neuen Rust-basierten Python-Type-Checker Pyrefly und Ty
(blog.edward-li.com)- Mit Pyrefly von Meta und Ty von Astral wurden kürzlich zwei Rust-basierte Python-Type-Checker vorgestellt, die gegenüber mypy und pyright überragende Leistung und ein neues Typing-Paradigma zeigen
- Pyrefly setzt auf aggressive Typinferenz und Open Source, während Ty mit dem Prinzip der „gradual guarantee“ darauf abzielt, das Auftreten von Typfehlern zu minimieren
- Beide Werkzeuge befinden sich noch in einer frühen Alpha-Version, aber Benchmarks in verschiedenen Projekten zeigen, dass Ty im Durchschnitt schneller läuft
- Bei der inkrementellen Analyse arbeitet Pyrefly auf Modulebene, während Ty eine feinere Inkrementalisierung bis auf Funktionszielebene bietet, was zu Unterschieden bei Nutzung und Struktur führt
- Ty präsentiert innovative Typensysteme wie Schnittmengentypen und Negationstypen und bietet intuitivere und klarere Fehlermeldungen
Einführung in Pyrefly und Ty
- Pyrefly und Ty sind in Rust entwickelte Python-Type-Checker
- Pyrefly wurde von Meta (ehemals Facebook) entwickelt und ersetzt das bisherige OCaml-basierte Pyre
- Ty wird von Astral entwickelt; Astral ist für Python-Tools wie uv und ruff bekannt
- Beide Projekte sind als Open Source veröffentlicht, befinden sich aber noch in der Alpha-Phase vor dem offiziellen Release
- Beide Teams stellten auf dem PyCon 2025 Typing Summit ihre Vision, Ziele und Ansätze vor
Gemeinsamkeiten
- Beide sind in Rust entwickelt und unterstützen inkrementelle Analyse (Incremental Checking)
- Für das AST-Parsing von Python-Code verwenden sie ruff
- Auch die Anbindung an Entwicklungsumgebungen ist stark, etwa durch Kommandozeilen-Typprüfung und Unterstützung für LSP-/IDE-Integration
Unterschied 1: Geschwindigkeit
PyTorch-Benchmark
- Ty ist etwa 2- bis 3-mal schneller als Pyrefly, und beide sind 10- bis 20-mal schneller als mypy und pyright
- Pyrefly zielt auf eine 35-fache Leistungssteigerung gegenüber Pyre und eine 14-fache gegenüber mypy/pyright
- Ty wurde mit dem Ziel entwickelt, ein- bis zweistellig schneller als die aktuelle Generation von Type-Checkern zu sein
Django-Benchmark
- Ty ist am schnellsten, gefolgt von Pyrefly
- Pyright zeigt ein deutlich langsameres Ergebnis
Benchmark des mypy-Repositorys
- Mit ähnlichem Ergebnis ist Ty am schnellsten, während Pyrefly mit geringem Abstand folgt
- mypy und pyright weisen deutlich längere Laufzeiten auf
Unterschied 2: Typing-Ziele
Pyrefly
- Verfolgt die Strategie, Typen so weit wie möglich zu inferieren, auch wenn im Code keine expliziten Typen angegeben sind, um Fehler zu erkennen
- Zielt mit noch aggressiverer Typinferenz auf maximale Code-Stabilität
Ty
- Wendet das Prinzip der gradual guarantee an
- Ist so entworfen, dass in funktionierendem Code beim Entfernen expliziter Typen keine Typfehler entstehen
- Verursacht auch ohne Typannotationen keine Fehler und verlangt zusätzliche Annotationen nur dann, wenn sie wirklich nötig sind
- Beispiel: Selbst wenn einem Feld ohne expliziten Typ ein Wert zugewiesen wird, entsteht kein Typfehler; stattdessen wird es etwa als
Unknown | Nonebehandelt
Unterschied 3: Verfahren der inkrementellen Analyse
- Pyrefly: Analysiert nur geänderte Dateien (Module) und deren abhängige Module neu (Inkrementalisierung auf Modulebene)
- Ty: Nutzt das Rust-Framework Salsa für eine feingranulare Inkrementalisierung bis auf Funktionsebene
- Modulebene gilt als ausreichend schnell, während Funktionsebene die Codebasis komplexer machen kann; darin unterscheiden sich die Strategien beider Tools
Unterschied 4: Funktionen (Typensystem und Unterstützung)
Stärken von Pyrefly
- Implizite Typinferenz ist sehr leistungsfähig
- Auch ohne explizite Typen analysiert es komplexe Typen wie Funktionsrückgaben, Dictionaries und Listen und erkennt Fehler
- Konzentriert sich bei der Entwicklung auf komplexe Typing-Probleme wie Generics, Overloads und Wildcard-Imports
- Die Genauigkeit bei der Inferenz generischer Typen ist höher als bei Ty
Besonderheiten von Ty
- Durch die „gradual guarantee“ sind Typänderungen auch ohne explizite Typen frei möglich
- Unterstützt innovative Typensysteme wie Schnittmengentypen (Intersection Types) und Negationstypen (Negation Types)
- Fehlermeldungen sind sehr klar und intuitiv gestaltet
- Erlaubt freie Zuweisung unterschiedlicher Typen etwa in Listen und führt den Typwert
Unknownsystematisch ein
Einschränkungen/Alpha-Status
- Beide Produkte befinden sich noch in der Alpha-Phase, daher sind Teile der Typinferenz oder einzelner Funktionen noch unvollständig
- Zum Beispiel ist bei Ty die Typinferenz für Listen in manchen Fällen noch nicht ausgereift
Detaillierter Funktionsvergleich
Implizite Typinferenz
- Pyrefly inferiert Rückgabetypen und Typen von Collection-Objekten aktiv und zeigt revealed type sowie Fehler klar an
- Ty gibt bei unzureichender Inferenz
Unknownoder@Todozurück
Generics
- Sowohl Pyrefly als auch Ty lösen typische Probleme mit generischen Typen gut
- Pyrefly ist bei der Interpretation des Typs von ohne Typparameter erzeugten Instanzen im Vorteil
- Beide Checker zeigen bei Kovarianz/Kontravarianz-Problemen (covariance/contravariance) Schwächen gegenüber mypy und pyright
Fehlermeldungen
- Ty legt den Schwerpunkt auf knappe und gut lesbare Fehlermeldungen
- Gegenüber Pyrefly, mypy und pyright bietet es Meldungen, die sich auf einen Blick leichter verstehen lassen
Schnittmengen-/Negationstypen
-
Nur Ty unterstützt Schnittmengentypen (
&) und Negationstypen (~) und kann damit komplexe Typoperationen wie die folgenden verarbeiten- Beispiel: Wenn in einem Typ
WithX | Otherdas Attributxvorhanden ist, verzweigt Ty automatisch zuWithX - Beispiel: Wenn es sich nicht um eine bestimmte Subklasse handelt, wird der Typ als
MyClass & ~MySubclassinterpretiert
- Beispiel: Wenn in einem Typ
-
Solche Schnittmengen- und Negationstypen sind in der Typentheorie sehr fortgeschrittene Funktionen
Weitere fortgeschrittene Beispiele
- Ty kann mit seinem Typensystem auch für komplexe Operationen wie diophantische Gleichungen genutzt werden
- Tests werden als Markdown-Dokumente geschrieben (Referenz: mdtest-Ressourcen von Astral ruff)
Fazit und Ausblick
- Im Python-Ökosystem sind damit überragend schnelle, neue Type-Checker erschienen
- Ty setzt als Hauptstrategie auf graduelle Typstabilität, Pyrefly auf aktive Typinferenz
- Beide Tools stehen noch am Anfang, sodass ihre Funktionen künftig noch zusammenlaufen oder sich weiterentwickeln können
- Sie lassen sich auf den offiziellen Websites ausprobieren, und es gibt Plugins für wichtige Editoren wie VSCode und Cursor
- Außerdem gibt es Gerüchte, dass auch Google einen Go-basierten Type-Checker als Open Source veröffentlichen will, was den Bereich der Python-Typanalyse weiter bereichern dürfte
Nutzung/Referenzen
- Pyrefly: pyrefly.org/sandbox
- Ty: play.ty.dev
- Astrals Ty nutzt Markdown-basierte Tests (genauer Pfad siehe mdtest im ruff-Repository)
- Offizielle Dokumentation, Editor-Plugins und Paket-Installationsbefehle sind ebenfalls verfügbar
2 Kommentare
Bei ty ist es offenbar so, dass der Rückgabetyp einer verwendeten Funktion immer
unknownist, wenn er nicht angegeben wird; geprüft wird erst nach dem Speichern.Pyrefly leitet ihn auch ohne Angabe her und prüft sogar schon während der Eingabe.
Hacker-News-Kommentare
Ein
ty-Entwickler betont, dass er sich freut, dasstyundpyreflyzunehmend Aufmerksamkeit bekommen, weist aber noch einmal darauf hin, dass beide Projekte noch nicht fertig sind; es gebe auch Beispiele wegen noch nicht implementierter Funktionen, und wenn man denkt „das ist seltsam“, könne es in Wirklichkeit sein, dass dieser Teil einfach noch nicht entwickelt wurde; man müsse berücksichtigen, dass Python eine enorm große und vielfältige Sprache istJemand meint, ihm gefalle der Markdown-Stil der Tests in
tywirklich sehr; dass die Tests zugleich als Dokumentation dienen, sei eine hervorragende Idee; er fragt, ob diese Vorgehensweise von den dokumentierten Codebeispielen in Rust inspiriert seiDass die Stellen, an denen Typen sichtbar gemacht werden, mit
@TODOmarkiert sind, fand jemand zunächst lustig, hält es bei näherem Nachdenken aber für einen ziemlich cleveren und nützlichen KniffAus Sicht einer Person mit TypeScript-Erfahrung ist schon die Vielfalt der Versuche interessant, etwa Typinferenz, Type Narrowing und dass sich die einzelnen Python-Typechecker jeweils unterschiedlich verhalten; weiterhin werde dringend ein schneller und verlässlicher Typechecker gebraucht, und Python wirke in dieser Hinsicht deutlich zurückgefallen; ein Typechecker solle Produktivität und Zuverlässigkeit des Codes erhöhen, weshalb solche Projekte unterstützt werden
Aus Rust-Entwicklersicht kommt die Frage nach einer „Skriptsprache für Rust“ auf: Gibt es ein Netzwerk, das an einer Sprache forscht, die syntaktisch gut zu Rust passt, Rust-Typen nativ importieren kann und schnell kompiliert bzw. Hot Reload unterstützt? Es wird auch um Einschätzungen gebeten, ob Python diese Rolle vielleicht übernehmen könnte, selbst wenn die Syntax anders ist; dazu ein Link: https://news.ycombinator.com/item?id=44050222
Eine Außenperspektive von jemandem mit wenig Python-Erfahrung: Wer sich für Type Hints interessiert, sollte den Reddit-Beitrag https://www.reddit.com/r/Python/comments/10zdidm/why_type_hinting_sucks/ lesen; man solle den Beitrag nicht zu ernst nehmen, aber es wird betont, dass selbst mit guten Type-Tools zunächst „gute Praxis“ entscheidend ist; als Beispiel wird genannt, dass in großen Codebasen wie bei Django oder Meta konsistente Nutzung und strenge Typechecks nur möglich seien, wenn Entwickler dazu gebracht werden, empfohlene Konventionen einzuhalten; Python habe wie C++ zu viele Funktionen und ein zu großzügiges Runtime-Verhalten, sodass es am Ende leichter zu verwalten sei, wenn man nur einen Teil davon eingeschränkt nutze; welcher Teil das ist, könne jedoch je nach Person und Zweck unterschiedlich sein; das wird auch mit Fällen verglichen, in denen Rust-Entwickler wegen strengerer Typsysteme mit Linux-Kernel-Entwicklern aneinandergeraten
In einem der Top-Kommentare zu dem Reddit-Beitrag werde die Diskussion mit der Haltung abgetan, man könne ja einfach
Anyverwenden; dem wird entgegengehalten, dass in realen Fällen klarere Typdeklarationen künftige Änderungen an Bibliotheksfunktionen oder unerwartete Eingabewerte frühzeitig als Fehler hätten verhindern können; für wartbaren und verlässlichen Python-Code sei Typechecking daher unverzichtbarStatt zu viel Zeit und Aufwand in Python-Typechecking zu stecken, sei es womöglich besser, gleich auf eine passendere statisch typisierte Sprache zu wechseln und Python nur noch dort über eine Interop-Schicht einzusetzen, wo es nötig ist; das sei nicht immer möglich, aber es gebe die Sorge, dass viel Zeit damit verschwendet werde, Python in etwas hineinzuzwingen
Die mächtigen und komplexen Python-Funktionen wie Meta Classes, Deskriptoren, die Verwendung von
__call__,object.__new__, Name Mangling undself.__dict__werden kritisiert: Darin stecke zu viel Magie, was die Lesbarkeit des Codes stark verschlechtere; persönlich wolle man solche Funktionen nicht verwendenJemand fragt sich, woher es kommt, dass hier Meinungen geäußert werden, ohne die Sprache tatsächlich zu benutzen; Python-Entwickler nutzten sie im Alltag und verstünden sie tiefgehend, deshalb sei es seltsam, wenn Nichtnutzer die Sprache anhand externer Begründungen kritisieren; außerdem wird die Atmosphäre kritisiert, in der mit contrived examples, also künstlich konstruierten Beispielen, diskutiert wird
Eine Person mit langjähriger Python-Erfahrung sagt entschieden, der größte Fehler sei, Type Hints und Typechecker gar nicht erst zu verwenden
Das „gradual guarantee“ von
tywird als interessant beschrieben, also die Eigenschaft, dass auch nach dem Entfernen einer Typannotation kein Type Error entstehen sollte; das wirke besonders passend für Python mit viel dynamischem CodeEs wird daran erinnert, dass graduelle Typisierung eine Struktur sei, in der überall ein
anystehen könne, ohne dass auch nur eine Warnung erscheine; dadurch werde selbst in wichtigem Code keine vollständige Typsicherheit garantiert, was den Schutz unzureichend mache; auch aus Erfahrungen mitmypysei das ein gravierendes Problem gewesen, und es brauche unbedingt eine Möglichkeit zu deklarieren: „Diese Datei wird vollständig statisch typgeprüft“; graduelle Typisierung sei eher ein Anti-Pattern, und vielleicht wäre der Begriff „soft typing“ passenderFür bestehende Codebasen gebe es außer gradueller Typisierung praktisch keine Alternative; aus Erfahrung mit mehreren Legacy-Python-Codebasen, denen mit
mypyType Hints hinzugefügt wurden, sei ein „Opt-in auf Modulebene“ am vernünftigsten; fallspyreflydas nicht unterstütze, sei seine Praxistauglichkeit begrenzt; aus der Perspektive von LLM-Codegenerierung könne ein sehr schneller und strenger Typechecker aber durchaus nützlich seinDas erinnere an die frühe Einführung von TypeScript, bei der sanftes Onboarding für große bestehende Projekte wichtig war; man könne nach und nach
noImplicitAnyoderstrictpro Modul aktivieren und so am Ende in eine Umgebung mit starker Typprüfung übergehenAuch aus Sicht eines Rust-Programmierers wirkt das „gradual guarantee“ am sinnvollsten
Eine andere Person sagt, dass sie diese Form gradueller Typunterstützung persönlich wenig attraktiv finde; das dynamische Typsystem von Python sei von vornherein fragil, und der Zweck zusätzlicher Typannotationen bestehe zur Hälfte gerade darin, dieses Fehlverhalten unter Kontrolle zu bringen; deshalb seien Optionen wie
no-implicit-anyoder einstrict-Modus zwingend nötigDas Tooling von Astral bringe frische Energie in das Python-Ökosystem, aber es werden Fragen zur „Langfristperspektive“ gestellt: Wird es direkt in Python integriert? Ist es in fünf Jahren verschwunden? Kommt irgendwann ein Abo-basierter Rug Pull?
Über eine Business-Source-Lizenz könnte Astral Unternehmen womöglich dazu drängen, für produktive Deployments mit Astral-Tools ein Unternehmensabo oder Ähnliches abzuschließen; die aktuellen Produkte seien dafür nicht exakt gemacht, aber aus Sicht von Venture Capital liege ein ähnliches Modell nahe
In der offiziellen Ankündigung habe Astral ausdrücklich erklärt, auf Basis der Tools verschiedene Services verkaufen zu wollen; als Referenz dient https://astral.sh/blog/announcing-astral-the-company-behind-ruff
Solche Sorgen beträfen in Wahrheit nicht nur Astral, sondern jedes Projekt; insbesondere bei Tooling von Facebook bestehe mit der Zeit ein hohes Risiko, dass es nicht mehr gepflegt und faktisch „liegen gelassen“ wird; Nutzer müssten am Ende immer selbst das Risiko tragen
Es wird eine Aussage eines Reddit-Nutzers zitiert, wonach das grundlegende VC-Modell letztlich darauf setze, von FAANG übernommen zu werden oder so bedrohlich groß zu werden, dass eine Art
acqui-hireinteressant werde; auch bei Astral seien also Szenarien wie Übernahmen und anschließender Talenttransfer denkbarEs kursiert das Gerücht, Astral bereite inzwischen auch Tools speziell für Großunternehmen vor, etwa eine gehostete private Paket-Registry
Am Beispiel
my_list = [1, 2, 3]wird kritisiert, dassmypy,pyreflyundpyrightmy_list.append("foo")als Type Error ansehen,tydies aber ohne zusätzliche Angabe erlaubt; in der Praxis seien Listen mit nur einem Typ der Normalfall, deshalb sollte ein Typechecker davon ausgehen; nur weil Python es zulasse, dürfe die Typprüfung nicht lasch werden; es wird scharf kritisiert, ob das nicht eine Politik sei, die auf Anfänger-Code optimiert istEin
ty-Entwickler erklärt dazu, dass die Typinferenz für Listenliterale noch nicht fertig sei; aktuell werde einfachlist[Unknown]verwendet, undUnknownsei ein gradual type ähnlich wieAny, wodurchappendfür alles erlaubt sei; es gebe Pläne für präzisere Inferenz, dazu wird auf das Issue https://github.com/astral-sh/ty/issues/168 verwiesenEine andere Meinung ist, dass es weniger um Optimierung für Anfänger gehe als um unvermeidliche Kompatibilität mit Legacy-Code; wenn man in große untypisierte Codebasen einen Typechecker einführen wolle, müsse bestehender Code möglichst unverändert weiterlaufen können, damit die Einstiegshürde niedrig bleibe
Dem wird widersprochen mit dem Argument, es sei nicht überzeugend, Tooling auf Basis persönlicher Ansichten zu bauen und dabei zu ignorieren, was Python tatsächlich erlaubt
Als Problem des
pyrefly-Ansatzes wird genannt, dass eine flächendeckende Einführung in großen untypisierten Codebasen schwierig sei; man müsse den Code einzeln anpassen, und ohne organisatorischen Konsens sei das kaum machbar; an Orten wie Meta, wo so etwas intern durchgesetzt werden könne, funktioniere das vielleicht, aber für eine graduelle Einführung sei ein toleranterer Ansatz wie beityrealistischer; zugleich wird angemerkt, dass man persönlich ein Tool bevorzugen würde, das bei gemischten Typen warntJemand meint, wenn es sich um ausführbaren Python-Code handle, dann sei es richtig, dass ohne explizite Typeinschränkung kein Type Error entstehe; wer ein strengeres statisches Subset wolle, könne die Typannotationen eben selbst hinzufügen
Ein erfahrener Nutzer meint, der Ansatz von Pyrefly strebe stärkere Typinferenz an, sodass in tatsächlich großen typsicheren Codebasen viel weniger Annotationen nötig seien; auch wenn die Einführung anfangs schwieriger sei, sei das langfristig effizienter;
tybefinde sich im Grunde in einem Zustand mit deaktiviertemnoImplicitAnyEs gibt die Hoffnung auf einen Typechecker mit ernsthafter Unterstützung für die Integration in Notebooks und Live Coding; statische Prüfung, die Fehler schon vor der Ausführung langer Zellen erkennt, wäre ein enormer Effizienzgewinn
Es wird nach Erfahrungen mit Jupyter-Notebooks in VSCode gefragt; dabei wird angemerkt, dass Typechecker wie
pylancebei experimentellem Code eher stören könntenEmpfohlen wird die Language-Server-Erfahrung von VSCode mit Notebook-Integration und unmittelbarem Feedback beim Live Coding; damit ließen sich Anforderungen an Notebook-Integration und interaktives Typechecking in Echtzeit lösen
Das Design von Pyrefly wirke ähnlich wie die Typinferenz von TypeScript und deshalb persönlich vernünftiger; als ideal wird eine graduelle, also inkrementelle Einführung auf Modulebene beschrieben; bis auf Funktionsebene hinunterzugehen sei zu kleinteilig und letztlich mehr als nötig; auch aus Performance-Sicht sei die Modulebene ausreichend
Selbst in Projekten mit viel Dynamik würde man wohl eine stärkere Typinferenz wie bei Pyrefly bevorzugen und trotz möglicher Unbequemlichkeiten eher diese Seite unterstützen
Derzeit wird
basedpyrightin IDE und CI verwendet, und die Stabilität wird grundsätzlich als zufriedenstellend angesehen;mypywird eher nicht gemocht, weil es selbst bei einfachen Typaufgaben oft scheitere