banner
Heim / Blog / Fix 2: Meta kommt als nächstes
Blog

Fix 2: Meta kommt als nächstes

Oct 16, 2023Oct 16, 2023

Python ist eine der am häufigsten bei Meta verwendeten Sprachen. Die Produktionsingenieure (PEs) von Meta sind spezialisierte Softwareentwickler (SWEs), die sich auf Zuverlässigkeit, Effizienz und Skalierbarkeit konzentrieren. Sie arbeiten an verschiedenen Projekten, darunter das Debuggen von Produktionsdiensten, das Umschreiben ineffizienter Bibliotheken, die Orchestrierung von Projektbereitstellungen im großen Maßstab oder die Kapazitätsplanung und -planung. Und Python ist oft eines der ersten Tools, nach denen PEs greifen, da es eine schnelle Entwicklung, eine leicht lesbare Syntax und eine riesige Auswahl an Open-Source-Bibliotheken bietet.

Das Python Language Foundation-Team von Meta – ein Hybridteam aus PEs und traditionellen SWEs – hilft bei der Verwaltung und Wartung der Infrastruktur und Tools für Python bei Meta. Das Team unterstützt Ingenieure, Datenwissenschaftler, Forscher und alle anderen bei Meta, die Python bei der Erledigung ihrer Arbeit verwenden.

Dies erreichen wir unter anderem durch die Entwicklung von Tools, die es Python-Entwicklern ermöglichen, besseren und zuverlässigeren Code effizienter zu schreiben. Dazu gehören Tools wie automatische Formatierung und Importsortierung, die Langeweile beseitigen, oder Linters, die Ingenieure zu wartbarem Code mit weniger Fehlern führen.

In diesem Jahr haben wir einen neuen Linter, Fixit 2, entwickelt, der von Grund auf entwickelt wurde, um Entwickler effizienter und leistungsfähiger zu machen, sowohl in Open-Source-Projekten als auch in der vielfältigen Landschaft unseres internen Monorepos. Bei Meta verwenden wir Fixit 2 mit einigen Early Adopters und planen, es bald auf den Rest unseres Monorepos auszurollen. Aber jeder Entwickler kann damit automatische Korrekturen effizienter durchführen und schneller Verbesserungen an seinen eigenen Codebasen vornehmen.

Es gibt eine Vielzahl hervorragender Linters im Python-Ökosystem, von denen viele über eine große Community von Drittanbieter-Plugins verfügen, die eine Vielzahl von Lint-Regeln bereitstellen. Wir verwenden Flake8 intern bei Meta seit 2016 und es hat Entwicklern sehr erfolgreich dabei geholfen, Fehler zu reduzieren und eine saubere Codebasis aufrechtzuerhalten. Das beliebte flake8-bugbear-Plugin wurde sogar von Łukasz Langa (Autor von Black, PSF-Developer-in-Residence und Release-Manager für Python 3.8 und 3.9) während seiner Arbeit bei Meta (damals Facebook) als Heimat für eigensinnigere Lint-Regeln erstellt die wir sowohl intern verwenden als auch mit dem Rest der Python-Entwicklergemeinschaft teilen könnten.

Wir haben auch eine große Anzahl interner Plugins, die von verschiedenen Teams erstellt wurden, und Flake8 ermöglicht es ihnen, benutzerdefinierte Lint-Regeln direkt in der Codebasis zu schreiben und zu aktivieren, ohne die Genehmigung eines zentralen Gatekeepers einzuholen und ohne auf den Beginn einer neuen Bereitstellung von Flake8 warten zu müssen aus.

Obwohl Flake8 seit langem ein Eckpfeiler unserer Flusenlösung ist, weist es auch einige Ecken und Kanten auf. Das Schreiben neuer Lint-Regeln erfordert die Erstellung ganzer Plugins (von denen jedes einen Teil des „Namespace“ für Fehlercodes beansprucht) und ermutigt Entwickler, komplizierte Plugins zu erstellen, die mehrere Fehlerklassen abdecken. Wenn diese Lint-Fehler gefunden werden, kann Flake8 nur auf die Zeilen- und Spaltennummer verweisen, in der sie aufgetreten sind, hat aber keine Möglichkeit, dem Entwickler, der sich eine Liste der Lint-Ergebnisse ansieht, Änderungen vorzuschlagen, so dass er in einem Zustand des Versuchs und Irrtums bleibt, sie zu finden Veränderungen, die den Linter glücklich machen. Außerdem verwendet Flake8 das stdlib-AST-Modul, wodurch es nicht in der Lage ist, zukünftige Syntaxfunktionen zu analysieren und Entwickler dazu zwingt, auf ein Upgrade der Tools zu warten, bevor sie die glänzende neue Funktionalität nutzen können.

Natürlich gibt es Alternativen zu Flake8, aber viele von ihnen haben einen oder mehrere Nachteile:

Während einige dieser Funktionen nicht kritisch sind, ist das wichtigste für die Entwicklereffizienz das Anbieten automatischer Korrekturen – automatisch vorgeschlagene Änderungen, die die Lint-Regel erfüllen würden. Dies macht das Rätselraten bei der Verwendung eines Linters überflüssig und ermöglicht Benutzern, diese Änderungen nach Möglichkeit schnell zu überprüfen und zu akzeptieren, sodass der Linter nicht erneut ausgeführt werden muss, bis der Code endgültig sauber ist. Die Kombination dieser automatischen Korrekturen mit benutzerdefinierten In-Repo-Lint-Regeln bietet ein Maß an maßgeschneiderten Verbesserungen der Codequalität, das kaum zu übertreffen ist.

Leider unterstützte selbst Fixit, der automatisch reparierende Linter, den wir für Instagram erstellt haben und als Open Source verfügbar sind, keine lokalen Lint-Regeln oder hierarchische Konfiguration – Kernanforderungen für unser Monorepo, das Tausende von Projekten beherbergt, von denen viele selbst Open-Source-Projekte sind mit ihren eigenen, ausgeprägten Bedürfnissen an Flusen und CI. Wir haben viele Anfragen von Entwicklern erhalten, Fixit in unserem Monorepo zu unterstützen, aber es gab so viele Hürden, dass wir nur einen kleinen Satz von Sicherheits-Lint-Regeln unterstützen konnten, was die direkten Vorteile für unsere Python-Codebasis schmälerte.

Nach Gesprächen mit anderen Teams, insbesondere im schnell wachsenden KI/ML-Bereich, haben wir unsere Optionen geprüft und uns für eine teilweise Neufassung von Fixit entschieden. Wir haben die neue Version bewusst mit einer Open-Source-First-Mentalität entworfen und dabei vom ersten Tag an die Bedürfnisse und Anforderungen unserer eigenen Monorepos und Open-Source-Projekte berücksichtigt.

Das Framework und die Linting-Engine würden von Grund auf neu aufgebaut, während das Kerndesign der Lint-Regeln weitgehend unberührt bliebe. Das neue System bietet eine hierarchische Konfiguration basierend auf dem TOML-Format; Unterstützung für lokale In-Repo-Lint-Regeln ähnlich wie Flake8; und eine deutlich verbesserte CLI und API für die Integration mit anderen Tools und Automatisierung.

Fixit selbst baut auf einem anderen Instagram-Open-Source-Projekt, LibCST, auf, einem konkreten Syntaxbaum für Python mit einer Baum- und Knoten-API, die den Mustern des ast-Moduls in der Standardbibliothek folgt. Der „konkrete“ Teil von CST bedeutet, dass LibCST nach dem Parsen jeden Teil der Quelldatei in den resultierenden Baum einbezieht, einschließlich Leerzeichen, Kommentare und Formatierungselemente, die vom ast-Modul ignoriert werden. Dies ermöglicht es Fixit (und anderen von uns entwickelten Tools wie µsort), Quelldateien sicher zu ändern, ohne reguläre Ausdrücke zu verwenden oder das Risiko einer fehlerhaften Syntax einzugehen, und bildet die Grundlage dafür, dass Fixit automatische Korrekturen anbieten kann, die von den Lint-Regeln selbst vorgeschlagen werden .

Das Schreiben einer neuen Lint-Regel kann mit weniger als einem Dutzend Codezeilen erfolgen, und Testfälle werden inline definiert. Sie können es sogar direkt neben dem Code platzieren, den es lintieren soll:

Das Vorschlagen automatischer Korrekturen für den Benutzer ist so einfach wie das Einfügen eines neuen CST-Knotens beim Melden eines Fehlers:

Die Aktivierung dieser neuen Regel innerhalb der Codebasis des Projekts kann mit einer einfachen Konfigurationsänderung erfolgen:

Jetzt können wir unseren Linter gegen unser Projekt ausführen:

Der Befehl „lint“ zeigt nur Fehler und vorgeschlagene Änderungen an. Wenn wir den Befehl „fix“ verwenden, können wir die vorgeschlagenen Änderungen wieder auf die Codebasis anwenden:

Nachdem unsere automatischen Korrekturen angewendet wurden, können wir bestätigen, dass das Projekt nun sauber und fusselfrei ist:

Wenn Fixit 2 mit automatisch reparierenden Lint-Regeln ausgeführt wird, bietet jeder Code, der die Lint-Regel auslöst, die Möglichkeit, einen automatischen Ersatz zu erhalten, wodurch die Codebasis mit weniger Aufwand für den Entwickler verbessert wird. Im weiteren Sinne kann Fixit 2 sogar als Werkzeug verwendet werden, um umfassende Codemods für eine große Codebasis umzusetzen, während eine Lint-Regel beibehalten wird, um künftig jeden passenden Code zu verarbeiten.

Fixit 2 ist ab heute auf PyPI verfügbar. Sie können Fixit 2 mit pip install fixit installieren und testen.

Wir haben eine Roadmap mit Plänen für zukünftige Verbesserungen und Funktionen sowie eine umfangreiche Dokumentation und Benutzerhandbücher, die Ihnen den Einstieg in Fixit 2 in Ihren eigenen Projekten oder Repositorys erleichtern. Wir hoffen, dass es sich bei Ihren Projekten als nützlich erweisen wird, und freuen uns auf Ihr Feedback!