- Stacked pull requests, die große Änderungen in kleine, überprüfbare Ebenen aufteilen, werden als öffentliche Preview schrittweise für alle Repositories bereitgestellt
- Jede PR zielt auf die direkt darunterliegende Ebene, sodass Teammitglieder eng begrenzte Diffs parallel und unabhängig reviewen können
- Wird die neueste PR gemergt, werden auch die darunterliegenden noch nicht gemergten Ebenen auf einmal übernommen; wenn nur ein Teil gemergt wird, werden die darüberliegenden PRs automatisch rebased und auf ein neues Ziel umgestellt
- Bestehende PR-Reviews, erforderliche Checks, Branch Protection und Merge-Anforderungen gelten unverändert; Stacks lassen sich auf GitHub.com, über die CLI, in der mobilen App und mit GitHub Copilot bearbeiten
- Die öffentliche Preview wird über einige Tage hinweg auf alle Repositories ausgeweitet; Merge-queue-Unterstützung wird in den folgenden Wochen schrittweise bereitgestellt
PR-Struktur für gestapelte kleine Änderungen
- Große Änderungen werden in mehrere kleine, fokussierte PRs aufgeteilt und jede PR als geordnete Änderungsebene organisiert
- Nachdem ein Branch und eine PR für die erste Änderung erstellt wurden, werden darüber weitere Branches und PRs hinzugefügt; jede PR zielt auf die direkt darunterliegende Ebene
- Verringert den Aufwand, eine einzelne große PR zu reviewen oder mehrere Branches ständig manuell rebasen zu müssen
- Das Next.js-Team bewertet, dass sich durch kleine einzelne Änderungen auch bei der Veröffentlichung großer Features PR-Reviews einfacher durchführen lassen
Stack-Erstellung und Arbeitsumgebung
- Die CLI-Erweiterung wird mit folgendem Befehl installiert
gh extension install github/gh-stack
- Stacks können auf GitHub.com, über die GitHub CLI und in der mobilen GitHub-App erstellt und verwaltet werden
- In Coding Agents wie GitHub Copilot kann der
gh-stack-Skill genutzt werden
Unabhängiges Review je Ebene
- Wird eine PR innerhalb eines Stacks geöffnet, lässt sich nur der Diff dieser Ebene statt der gesamten Änderung reviewen
- Über die Stack-Map oben in der PR ist erkennbar, wo sich die aktuelle Änderung innerhalb der Gesamtarbeit befindet
- Teammitglieder können unterschiedliche Ebenen parallel reviewen, sodass nachgelagerte Arbeit nicht bis zum Abschluss eines Reviews blockiert wird
- Bestehende Branch-Protection-Regeln und Reviews je Ebene können kombiniert werden, um die Qualität jedes Schritts zu steuern
- TED erklärte, dass nach gestiegener Entwicklungsproduktivität durch den Einsatz von KI größere PRs zu einem Review-Flaschenhals wurden; durch die Aufteilung von Änderungen in kleine logische Einheiten entlang ihrer Abhängigkeiten konnten Review-Geschwindigkeit und Genauigkeit erhöht werden
Gesamten oder teilweisen Stack mergen
- Wird die neueste PR gemergt, sobald sie bereit ist, werden diese PR und alle darunterliegenden noch nicht gemergten Ebenen auf einmal übernommen
- Es ist auch möglich, zunächst nur einen Teil des Stacks zu mergen, indem eine oder mehrere untere Ebenen ausgewählt werden
- Die darüberliegenden PRs bleiben geöffnet
- Sie werden automatisch auf die gemergten Änderungen rebased und ihr Ziel-Branch wird ebenfalls geändert
- Bestehende Branch Protection, erforderliche Checks und Merge-Anforderungen gelten weiterhin und steuern, welche Änderungen in
main gelangen
- Neben dem gesamten Stack können auch eine einzelne Ebene oder ausgewählte Ebenen gemergt werden
Öffentliche Preview und Zeitplan für Unterstützung
- Stacked pull requests werden über einige Tage hinweg als öffentliche Preview schrittweise für alle Repositories ausgerollt
- Unterstützung für die Merge queue wird in den folgenden Wochen schrittweise ausgerollt
- Eine ausführliche Anleitung findet sich in der Dokumentation zu stacked pull requests; Feedback wird in der stacks discussion entgegengenommen
1 Kommentare
Hacker-News-Kommentare
Ich habe die Preview eine Weile benutzt, und es überrascht mich, dass der Kreis der Nutzer erweitert wird, obwohl noch viele Probleme ungelöst sind.
Zum Beispiel ist das Mergen eines ganzen Stacks in mehreren Situationen völlig kaputt: https://github.com/github/gh-stack/discussions/212
Man kann zwar einzeln mergen, aber wenn man Squash Merge zusammen mit verpflichtenden Reviews verwendet, muss man für jedes PR im Stack erneut eine Freigabe einholen, wodurch der größte Vorteil von Stack-PRs verloren geht.
gh stackspart etwas Handarbeit, aber man mussgit rebasetrotzdem genau verstehen. Wenn der lokale Branch nicht mit dem Remote synchronisiert ist, schlägt auch das im UI empfohlenegh stack rebasefehl, und das Tool sagt nicht, warum.Andererseits gefällt mir das Stack-UI, weil es einfach ist und die Beziehungen zwischen den PRs dennoch ausreichend zeigt. Es macht nur den Workflow bequemer, vorausgesetzt, es gibt bereits einen Grund, PRs zu stapeln; es ist kein Tool, das neue Funktionen bietet.
Das interne CPRMC (Create Pull Request Merge Commit) prüft zur Beurteilung der Merge-Bereitschaft eines PRs alles von möglichen Konflikten bis dazu, ob die Freigaben tatsächlich zu dem Commit passen, der erzeugt wird.
Um mehrere PRs per Squash zu mergen, muss man eine Folge von Squash-Commits berechnen und sie dann wieder mit Regeln und Reviews verknüpfen. Beim ersten PR ist das noch relativ einfach, aber ab dem zweiten wird es komplex, weil die Vorfahren-Commits bereits per Squash zusammengeführt wurden und im Branch nicht mehr in ihrer ursprünglichen Form existieren; bei Situationen mit mehreren Eltern-Commits ist es noch viel schwieriger.
Derzeit sind 99 % der Stack-Merges erfolgreich, und dieses Verhältnis deutlich zu erhöhen ist die höchste Priorität des Teams.
merginghängen bleibt, nachdem ich den Branch gelöscht hatte, auf den ein Stack-PR zeigte, ohne weitere Hinweise.Ich habe sogar auf der GitHub-Statusseite nachgesehen, weil ich dachte, es sei ein teilweiser Ausfall des PR-Systems, aber es war ein Bug der Stack-PR-Funktion selbst.
Das GitHub-Stacked-PRs-Team macht es jetzt breiter verfügbar, sodass jeder einen Stack erstellen kann: https://gh.io/stacks
Gesucht wird insbesondere Feedback zu UI und CLI, und es sind noch viele Updates geplant, die die Nutzung von PRs verbessern sollen.
Es ist einer der größten Releases in der Geschichte von GitHub, weil er nahezu alle Dienste umfasst, von Actions und Schutzregeln bis zu CLI und Mobile App, daher können auch Fragen zu Designentscheidungen und interner Funktionsweise beantwortet werden.
Ich nutze ohnehin ein eigenes lokales UI, um die Abhängigkeiten von Stack-PRs als Baum zu sehen und den Review- und CI-Status jedes PRs zu verwalten, deshalb hätte ich gern Baum- und Statusanzeige auch im GitHub-Web-UI.
Im Web-UI scheint es nicht unterstützt zu werden, nur das unterste PR im Stack zu mergen, aber weil sich Workflow und Code wiederverwenden lassen, hoffe ich, dass das auch in die Standard-Tools von GitHub kommt.
Für öffentliche Repositories wirkt das wie eine wichtige Funktion, daher überrascht es mich, dass sie nicht schon vor der öffentlichen Preview bereitstand.
Gab es einen besonderen Gedanken dahinter, statt eines brauchbaren UIs zum Reviewen, Anwenden und Überarbeiten auf Commit-Ebene den Patchset-Workflow von Mailinglisten, dem eigentlichen Vorbild dieses Ansatzes, zu ignorieren und faktisch ein „Patchset aus Patchsets“ zu wählen?
Eine der größten Änderungen, die seit Jahren bei GitHub eingeführt wurden.
Dadurch, dass ein Stack-Workflow auf einer der größten Code-Hosting-Plattformen der Welt eingeführt wird, könnten viele Entwickler erstmals mit einem Ansatz in Kontakt kommen, von dessen Existenz sie bisher nicht einmal wussten.
Falls die Annahme stimmt, dass Stacks zu besserer Software führen, könnte das tatsächlich sehr vielen Entwicklern helfen.
Ich frage mich, was der Vorteil solcher Stack-PRs im Vergleich dazu ist, sauber aufbereitete Commits einzeln zu reviewen.
Das größere Problem ist, dass große AI-generierte PRs eine eigene Form des Reviews brauchen. Schon allein die Reihenfolge, in der Diffs angezeigt werden — etwa erst Funktionsdefinitionen, dann Aufrufstellen, dann Tests — macht einen großen Unterschied dafür, wie gut sie lesbar sind.
So wie Literate Programming Code und Prosa verwebt, könnte man vielleicht literate Diffs oder literate PRs brauchen, die Diffs und Erklärungen kombinieren, aber ich habe noch kein ähnliches Tool gefunden.
Weil die Review-Einheit, also PR oder Diff, eine einzelne begrenzte Änderung bleibt, konzentriert sich die Diskussion auf diese Änderung, und selbst wenn die Funktion größer wird, bläht sich das PR selbst nicht auf.
Außerdem kann man die einzelnen Teile des Stacks unterschiedlichen Zielgruppen zuweisen. Wenn man Reviewer nach externen Teams, Teamkollegen oder Teams aufteilt, die die Änderung nutzen, ist nicht unklar, was jeweils freigegeben wird.
GitHub-Reviews wären noch besser, wenn Change IDs eingeführt würden, damit Kommentare auch nach einem Rebase erhalten bleiben.
Dass man danach die folgenden PRs rebasen und anpassen muss, ist dasselbe wie das Korrigieren späterer Commits in einem riesigen einzelnen PR, aber statt überall zufällig temporäre Fixup-Commits an die gesamte Änderung anzuhängen, bleiben die Commits der zugrunde liegenden Änderung leichter zusammen.
Auch die Diskussion zur Basisänderung bleibt gebündelt, und wenn der gesamte Stack früh sichtbar ist, können Reviewer die endgültige Richtung verstehen, während die Arbeit asynchron weiterläuft.
Sie benutzen Commits wie Spielstände, hinterlassen nur Nachrichten wie
fix bugoderdo workund räumen sie nicht mitgit rebase -iauf; wenn man also verpflichtende Squash-Merges nicht aktiviert, ist das Log voller Müll-Commits.Für solche Entwickler ist ein PR praktisch ein Commit, und mit Stack-PRs können sie endlich eine Struktur nutzen, die mehreren Commits ähnelt, aus denen eine einzelne Änderung besteht.
Gemergte Diffs kann man auf den aktuellen HEAD rebasen, und in Teams, die das unterstützen, verwaltet man Branches meist nicht direkt, sondern arbeitet auf dem Trunk und rebased bei jeder eingehenden Änderung.
Wenn die ersten vier Teile einer Funktion fertig sind und es beim fünften ein Problem gibt, muss nicht alles blockiert werden.
Ich frage mich, wann Fälle unterstützt werden, in denen abhängige PRs keine lineare Historie, sondern eine Baumstruktur bilden.
Als wir bei Google gestapelte Änderungen verwendet haben, kam das häufig vor, und jetzt mit mehr parallelen Coding-Agenten dürfte es noch öfter auftreten.
Ich frage mich, ob der Umschaltknopf im Menü ein Stapel-Pancake-Emoji (U+1F95E) ist, weil es um Stacks geht.
Der verspielte Ausdruck an sich ist in Ordnung, aber es war eine UI, die starke Zweifel daran auslöste, was man da eigentlich sieht.
Es soll nur ein paar Stunden angezeigt und dann wieder durch ein normales Icon ersetzt werden.
Seit ich zum ersten Mal davon gehört habe, nutze ich die
gh stack-CLI, und das Tool selbst ist sehr gut, aber die Web-UI, zu der ich nach Freischaltung der Preview Zugang bekam, blieb weit hinter den Erwartungen zurück.Schon vor der Freischaltung machte die CLI die Automatisierung einfach, Arbeit in mehrere atomare PRs aufzuteilen, aber nach dem Pushen wurden sie als voneinander unabhängige PRs ohne Verbindung dargestellt.
Nach der Freischaltung ist es fast genauso; der einzige Unterschied ist, dass in einem kleinen Navigations-Dropdown oben andere PRs aus demselben Stack angezeigt werden, also keine sinnvolle UI-Änderung.
Im Dropdown kann man einige CLI-Funktionen ausführen, aber das ist eher eine nebensächliche Bequemlichkeit wie das Bearbeiten von Dateien im Web, und im eigentlichen Entwicklungs-Workflow werden die CLI oder ein IDE-Plugin im Mittelpunkt stehen.
Ich frage mich, warum man für so eine optionale UI die allgemeine Veröffentlichung so lange hinausgezögert hat; die Stack-CLI war seit der Ankündigung bereits allgemein verfügbar.
Dazu gehört auch eine Ansicht, die den Stack dauerhaft sichtbar macht, ihn immer mitdenkt und es ermöglicht, ohne viele Klicks zwischen den Ebenen zu wechseln.
An jujutsu gefällt mir, dass beim Aktualisieren eines Branches auch andere Branches, die von diesem Branch abgezweigt sind, automatisch neu rebased werden.
Wenn ich Arbeit zur leichteren Review aufteile, wechsle ich oft zu
jj, und es funktioniert gut, im selben Working Directory gemeinsam verwendet mit einem in Git erstellten Klon.jj absorbist ebenfalls großartig.Es verschiebt Änderungen zur nächstliegenden relevanten Änderung, sodass sich Korrekturen, die mehrere PRs betreffen, leicht handhaben lassen.
Nachdem ich Graphite verwendet habe, war es sehr schwer, zu GitHub ohne Stacks zurückzukehren.
Ich hoffe, dass mit der Unterstützung von GitHub Workflows mit gestapelten PRs verbreitet werden und es eine einfache Alternative zu riesigen PRs gibt.
git-spice.Es ist einfach zu benutzen und ein leistungsstarkes Open-Source-Tool; Graphite wirkte im Verhältnis zu seinen Funktionen unnötig komplex.
Soweit ich es verstanden habe, ist das Stapeln von PRs in zwei Situationen nützlich.
Erstens, wenn sie sich über mehrere zusammenhängende Repositories erstrecken und sich deshalb nicht zu einer einzigen PR zusammenfassen lassen, und zweitens, wenn man während der Review der ersten PR weitere PRs auf demselben Branch aufbaut, um die Arbeit zu pipelineisieren.
Diese Funktion erfüllt aber offenbar keines von beidem und wirkt eher wie eine andere Form, Commits in einer einzelnen PR zu stapeln.
Normalerweise erstellt man atomare und aussagekräftige Commits und strukturiert den Verlauf per Rebase so, dass er für Reviewer gut nachvollziehbar ist; Reviewer können ihn bei Bedarf auch commitweise durchgehen.
Ich frage mich, welchen eigenständigen Vorteil dieser Ansatz bietet, den ich dabei übersehe.