Veröffentlicht am: 18. August 2025

10 Minuten Lesezeit

Was ist neu in Git 2.51.0?

Erfahren Sie mehr über die neuesten Beiträge von GitLabs Git-Team und der Git-Community, einschließlich Performance-Optimierungen für git-push(1) und git-fetch(1), die besonders für deutsche Entwicklungsteams relevant sind.

Das Git-Projekt hat kürzlich Git 2.51 veröffentlicht. Aufgrund des Sommers auf der Nordhalbkugel und langsamerer Fortschritte war dieser Release-Zyklus mit 8 Wochen eher kurz (normalerweise dauert ein Release-Zyklus etwa 12 Wochen).

Die wichtigste Neuerung: Git-Operationen werden bis zu 22-mal schneller - besonders bei großen Repositories mit vielen Branches profitieren Entwicklungsteams von erheblichen Performance-Verbesserungen.

Schauen wir uns diese und andere bemerkenswerte Änderungen in diesem Release an, einschließlich Beiträgen vom Git-Team bei GitLab und der breiteren Git-Community.

Massive Performance-Verbesserungen: Von Sekunden zu Millisekunden

Große Repositories mit tausenden von Branches standen vor einem schmerzhaften Engpass. Git-Operationen, die Referenzen aktualisieren, konnten mehrere Sekunden dauern - ein echter Produktivitätskiller für Teams mit umfangreichen CI/CD-Pipelines oder Monorepo-Workflows.

Git 2.51.0 ändert alles. Eine 10.000-Referenzen-Fetch-Operation, die 3,4 Sekunden dauerte, wird jetzt in 154 Millisekunden abgeschlossen:

VORHER: git-fetch mit 10.000 Referenzen
Time: 3.403 s ± 0.775 s

NACHHER: git-fetch mit 10.000 Referenzen  
Time: 154.3 ms ± 17.6 ms

ERGEBNIS: 22× schneller

Ähnlich dramatische Verbesserungen bei git-push:

VORHER: git-push mit 10.000 Referenzen
Time: 4.276 s ± 0.078 s

NACHHER: git-push mit 10.000 Referenzen
Time: 235.4 ms ± 6.9 ms

ERGEBNIS: 18× schneller

Wie wurde das erreicht?

Das Problem lag in der Art, wie Git Referenz-Transaktionen behandelte. Die Kommandos git-push(1) und git-fetch(1) erstellten eine separate Transaktion für jedes Referenz-Update, was enormen Overhead verursachte - jede Transaktion benötigte eine Initialisierungs- und Abbauphase und löste Auto-Komprimierungen aus.

Git 2.51.0 verwendet nun gebündelte Updates: Mehrere Referenzen werden in einer einzigen Transaktion aktualisiert, während einzelne Updates weiterhin fehlschlagen dürfen. Dies eliminiert den Overhead und skaliert linear mit der Anzahl der Referenzen.

Das Beste daran? Benutzer profitieren automatisch von diesen Verbesserungen, ohne Änderungen an ihrem Workflow vornehmen zu müssen.

Dieses Projekt wurde von Karthik Nayak geleitet.

Änderungen in Richtung Git 3.0

Vor 11 Jahren wurde Git 2.0 veröffentlicht, die letzte große Versionsfreigabe von Git. Obwohl wir keinen spezifischen Zeitplan für die nächste große Git-Veröffentlichung haben, enthält dieses Release Entscheidungen, die in Richtung Git 3.0 getroffen wurden.

Die Git 3.0-Release-Planung ermöglicht es uns, Breaking Changes zu planen und zu implementieren und diese der erweiterten Git-Community zu kommunizieren. Neben der Dokumentation kann Git auch mit diesen Breaking Changes kompiliert werden für diejenigen, die mit diesen Änderungen experimentieren möchten. Weitere Informationen finden Sie im BreakingChanges-Dokument.

Das Git 2.51.0-Release bringt einige bedeutende Änderungen in Richtung Git 3.0.

"reftable" wird Standard in Git 3.0

Im Git 2.45.0-Release wurde das "reftable"-Format als neues Backend zur Speicherung von Referenzen wie Branches oder Tags in Git eingeführt, das viele der Probleme des bestehenden "files"-Backends behebt. Lesen Sie unseren Einsteiger-Leitfaden zur Funktionsweise von reftables für weitere Einblicke in das "reftable"-Backend.

Das Git 2.51.0-Release markiert den Wechsel zur Verwendung des "reftable"-Formats als Standard in Git 3.0 für neu erstellte Repositories und verdrahtet die Änderung hinter einem Feature-Flag. Das "reftable"-Format bietet folgende Verbesserungen gegenüber dem traditionellen "files"-Backend:

  • Es ist unmöglich, zwei Referenzen zu speichern, die sich nur in der Groß-/Kleinschreibung unterscheiden, auf case-insensitiven Dateisystemen mit dem "files"-Format. Dieses Problem ist häufig auf Windows- und macOS-Plattformen. Da das "reftable"-Backend keine Dateisystem-Pfade zur Kodierung von Referenznamen verwendet, verschwindet dieses Problem.

  • Ebenso normalisiert macOS Pfadnamen, die Unicode-Zeichen enthalten, was zur Folge hat, dass Sie nicht zwei Namen mit Unicode-Zeichen speichern können, die unterschiedlich kodiert sind, mit dem "files"-Backend. Auch dies ist kein Problem mit dem "reftable"-Backend.

  • Das Löschen von Referenzen mit dem "files"-Backend erfordert, dass Git die komplette "packed-refs"-Datei neu schreibt. In großen Repositories mit vielen Referenzen kann diese Datei leicht dutzende Megabytes groß sein; in extremen Fällen kann sie Gigabytes umfassen. Das "reftable"-Backend verwendet Tombstone-Marker für gelöschte Referenzen und muss daher nicht alle seine Daten neu schreiben.

  • Repository-Hauskeeping mit dem "files"-Backend führt normalerweise All-into-One-Repacks von Referenzen durch. Dies kann sehr teuer sein, und folglich ist Housekeeping ein Kompromiss zwischen der Anzahl loser Referenzen, die sich ansammeln und Operationen verlangsamen, die Referenzen lesen, und der Komprimierung dieser losen Referenzen in die "packed-refs"-Datei. Das "reftable"-Backend verwendet geometrische Komprimierung nach jedem Schreibvorgang, was Kosten amortisiert und sicherstellt, dass das Backend immer in einem gut gewarteten Zustand ist.

  • Operationen, die mehrere Referenzen auf einmal schreiben, sind nicht atomisch mit dem "files"-Backend. Folglich kann Git Zwischenzustände sehen, wenn es Referenzen liest, während eine Referenz-Transaktion gerade auf die Festplatte committed wird.

  • Das Schreiben vieler Referenzen auf einmal ist langsam mit dem "files"-Backend, weil jede Referenz als separate Datei erstellt wird. Das "reftable"-Backend übertrifft das "files"-Backend um mehrere Größenordnungen.

  • Das "reftable"-Backend verwendet ein Binärformat mit Präfix-Komprimierung für Referenznamen. Als Resultat nutzt das Format weniger Platz im Vergleich zur "packed-refs"-Datei.

Dieses Projekt wurde von Patrick Steinhardt geleitet.

SHA-256 wird Standard in Git 3.0

Das Git-Versionskontrollsystem speichert Objekte in einem inhaltsadressierbaren Dateisystem. Das bedeutet, es verwendet den Hash eines Objekts zur Adressierung von Inhalten wie Dateien, Verzeichnissen und Revisionen, anders als traditionelle Dateisysteme, die sequenzielle Nummern verwenden. Die Verwendung einer Hash-Funktion hat folgende Vorteile:

  • Einfache Integritätsprüfungen, da ein einzelner Bit-Flip die Hash-Ausgabe komplett verändern würde.
  • Schnelle Objektsuche, da Objekte nach ihrem Hash indexiert werden können.
  • Objektnamen können signiert werden und Drittparteien können dem Hash vertrauen, um das signierte Objekt und alle Objekte, auf die es verweist, zu adressieren.
  • Kommunikation über Git-Protokoll und Out-of-Band-Kommunikationsmethoden haben einen kurzen zuverlässigen String, der zur zuverlässigen Adressierung gespeicherter Inhalte verwendet werden kann.

Seit seiner Entstehung hat Git den SHA-1-Hashing-Algorithmus verwendet. Sicherheitsforscher haben jedoch einige Schwachstellen in SHA-1 entdeckt, speziell den SHAttered-Angriff, der eine praktische SHA-1-Hash-Kollision zeigt. Wir sind seit Git 2.13.0 standardmäßig zu einer gehärteten SHA-1-Implementierung übergegangen. SHA-1 ist jedoch immer noch ein schwacher Hashing-Algorithmus und es ist nur eine Frage der Zeit, bis zusätzliche Angriffe seine Sicherheit weiter reduzieren werden.

SHA-256 wurde Ende 2018 als Nachfolger von SHA-1 identifiziert. Git 2.51.0 markiert es als Standard-Hash-Algorithmus für Git 3.0.

Dieses Projekt wurde von brian m. carlson geleitet.

Entfernung von git-whatchanged(1)

Der git-whatchanged(1)-Befehl zeigt Logs mit Unterschieden, die jeder Commit einführt. Obwohl dies nun von git log --raw abgelöst wurde, wurde der Befehl aus historischen Gründen beibehalten.

Git 2.51.0 erfordert, dass Benutzer des Befehls explizit das --i-still-use-this-Flag verwenden, um alle Benutzer zu erfassen, die noch den veralteten Befehl verwenden, und markiert den Befehl auch für die Entfernung in Git 3.0.

Dieses Projekt wurde von Junio C Hamano geleitet.

git switch und git restore sind nicht mehr experimentell

Der git-checkout(1)-Befehl kann für mehrere verschiedene Anwendungsfälle verwendet werden. Er kann zum Wechseln von Referenzen verwendet werden:

$ git status
Auf Zweig master
Ihr Branch ist auf dem neuesten Stand mit 'origin/master'.
Nichts zu committen, Arbeitsverzeichnis unverändert

$ git checkout next
Zu Branch 'next' gewechselt
Ihr Branch ist auf dem neuesten Stand mit 'origin/next'.

Oder zur Wiederherstellung von Dateien:

$ echo "additional line" >> git.c

$ git status
Auf Zweig master
Ihr Branch ist auf dem neuesten Stand mit 'origin/master'.

Änderungen, die nicht zum Commit vorgemerkt sind:
  (benutzen Sie "git add <Datei>...", um die Änderungen zum Commit vorzumerken)
  (benutzen Sie "git restore <Datei>...", um die Änderungen im Arbeitsverzeichnis zu verwerfen)
        geändert:       git.c

keine Änderungen zum Commit vorgemerkt (benutzen Sie "git add" und/oder "git commit -a")

$ git checkout git.c
1 Pfad von Index aktualisiert

$ git status
Auf Zweig master
Ihr Branch ist auf dem neuesten Stand mit 'origin/master'.
Nichts zu committen, Arbeitsverzeichnis unverändert

Für neue Git-Benutzer kann dies zu viel Verwirrung führen. In Git 2.33.0 wurden diese in zwei neue Befehle aufgeteilt: git-switch(1) und git-restore(1).

Der git-switch(1)-Befehl ermöglicht es Benutzern, zu einem bestimmten Branch zu wechseln:

$ git status
Auf Zweig master
Ihr Branch ist auf dem neuesten Stand mit 'origin/master'.
Nichts zu committen, Arbeitsverzeichnis unverändert

$ git switch next
Zu Branch 'next' gewechselt
Ihr Branch ist auf dem neuesten Stand mit 'origin/next'.

Und der git-restore(1)-Befehl ermöglicht es Benutzern, Working-Tree-Dateien wiederherzustellen:

$ echo "additional line" >> git.c

$ git status
Auf Zweig master
Ihr Branch ist auf dem neuesten Stand mit 'origin/master'.

Änderungen, die nicht zum Commit vorgemerkt sind:
  (benutzen Sie "git add <Datei>...", um die Änderungen zum Commit vorzumerken)
  (benutzen Sie "git restore <Datei>...", um die Änderungen im Arbeitsverzeichnis zu verwerfen)
        geändert:       git.c

keine Änderungen zum Commit vorgemerkt (benutzen Sie "git add" und/oder "git commit -a")

$ git restore git.c

$ git status
Auf Zweig master
Ihr Branch ist auf dem neuesten Stand mit 'origin/master'.
Nichts zu committen, Arbeitsverzeichnis unverändert

Obwohl die beiden Befehle seit 2019 existieren, wurden sie als experimentell markiert. Der Effekt ist, dass das Git-Projekt keine Rückwärtskompatibilität für diese Befehle garantiert: das Verhalten kann sich jederzeit ändern. Obwohl die Absicht ursprünglich war, diese Befehle nach einigen Releases zu stabilisieren, ist das bis zu diesem Punkt nicht geschehen.

Dies hat zu mehreren Diskussionen auf der Git-Mailing-Liste geführt, wo Benutzer unsicher sind, ob sie diese neuen Befehle verwenden können oder ob sie eventuell wieder verschwinden. Da jedoch keine bedeutenden Änderungen vorgeschlagen wurden und einige Benutzer diese Befehle bereits verwenden, haben wir beschlossen, sie in Git 2.51 nicht mehr als experimentell zu deklarieren.

Dieses Projekt wurde von Justin Tobler geleitet.

git for-each-ref(1) erhält Paginierungs-Unterstützung

Der git for-each-ref-Befehl wird verwendet, um alle im Repository vorhandenen Referenzen aufzulisten. Als Teil der Plumbing-Schicht von Git wird dieser Befehl häufig beispielsweise von Hosting-Forges verwendet, um Referenzen, die im Repository existieren, in ihrer UI aufzulisten. Aber während Repositories wachsen, wird es weniger realistisch, alle Referenzen auf einmal aufzulisten – schließlich können die größten Repositories Millionen davon enthalten! Stattdessen neigen Forges dazu, die Referenzen zu paginieren.

Dies zeigt eine wichtige Lücke auf: git-for-each-ref weiß nicht, Referenzen von vorherigen Seiten zu überspringen, die bereits gezeigt wurden. Folglich muss es möglicherweise eine große Anzahl uninteressanter Referenzen auflisten, bevor es endlich beginnt, die für die aktuelle Seite benötigten Referenzen zu liefern. Dies ist ineffizient und führt zu höherer als notwendiger Latenz oder sogar Timeouts.

Git 2.51.0 unterstützt ein neues --start-after-Flag für git for-each-ref, das die Paginierung der Ausgabe ermöglicht. Dies kann auch mit dem --count-Flag kombiniert werden, um über einen Batch von Referenzen zu iterieren.

$ git for-each-ref --count=10
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-001
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-002
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-003
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-004
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-005
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-006
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-007
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-008
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-009
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-010

$ git for-each-ref --count=10 --start-after=refs/heads/branch-010
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-011
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-012
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-013
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-014
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-015
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-016
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-017
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-018
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-019
9751243fba48b34d29aabfc9784803617a806e81 commit    refs/heads/branch-020

Dieses Projekt wurde von Karthik Nayak geleitet.

Fazit

Diese Performance-Verbesserungen sind besonders relevant für deutsche Entwicklungsteams, die mit großen Repositories und intensiven CI/CD-Workflows arbeiten. Die 22-fache Beschleunigung bei git-fetch kann erhebliche Zeitersparnisse in der täglichen Entwicklungsarbeit bedeuten.

Bereit, diese Verbeszerungen zu erleben? Aktualisieren Sie auf Git 2.51.0 und beginnen Sie, git switch und git restore in Ihrem täglichen Workflow zu verwenden.

Für GitLab-Benutzer werden diese Performance-Verbesserungen automatisch Ihre Entwicklungserfahrung verbessern, sobald Ihre Git-Version aktualisiert wird.

Erfahren Sie mehr in den offiziellen Git 2.51.0 Release Notes und erkunden Sie unser komplettes Archiv der Git-Entwicklungsberichterstattung.


Für vollständige technische Details, Benchmarks und Implementierungshinweise lesen Sie den englischen Originalartikel.

Wir möchten gern von dir hören

Hat dir dieser Blogbeitrag gefallen oder hast du Fragen oder Feedback? Erstelle ein neues Diskussionsthema im GitLab-Community-Forum und tausche deine Eindrücke aus.
Share your feedback

Mehr als 50 % der Fortune-100-Unternehmen vertrauen GitLab

Stelle jetzt bessere Software schneller bereit

Erlebe, was dein Team mit der intelligenten

DevSecOps-Plattform erreichen kann.