Kurs
In bestimmten Situationen wollen wir den Zustand eines lokalen Git-Branches auf den Stand des Remote-Repositories zurücksetzen und dabei alle lokalen Änderungen verwerfen. Das wird oft als erzwungener Pull bezeichnet.
Das führt leicht zum Irrglauben, man müsse dafür die Option --force im Befehl git pull verwenden. In diesem Artikel lernst du, dass das zwei verschiedene Dinge sind.
Wenn du neu bei Git bist, lies zuerst unser Tutorial zu Git push und pull.
Wir können unseren lokalen Stand mit dem Remote-Stand überschreiben, indem wir die folgenden Befehle ausführen und <branch_name> durch den Namen deines Branches ersetzen. Diese Aktion löscht dauerhaft alle lokalen Änderungen in diesem Branch.
git fetch
git reset --hard origin/<branch_name>
Dieser Artikel zeigt im Detail, wie diese Befehle funktionieren. Wir gehen über schnelle Lösungen hinaus, verstehen die Mechanik dahinter und lernen dadurch wirksamere Methoden kennen, um das gewünschte Ergebnis zu erreichen, ohne wichtige Änderungen zu verlieren. Außerdem räumen wir mit dem Missverständnis auf und klären, was die Option --force bei git pull tatsächlich bewirkt.
Werde Dateningenieur
Wann es sinnvoll ist, lokale Änderungen zu überschreiben
Grundsätzlich widerspricht dieses Überschreiben lokaler Änderungen der gedachten Arbeitsweise von Git. Für fast jede Situation gibt es einen passenden Git-Workflow. Allerdings erfordern einige davon ein tieferes Verständnis und brauchen mehr Zeit. Auch wenn es keine Best Practice ist, kann das Überschreiben lokaler Änderungen manchmal der schnellste Weg sein, um weiterzukommen.
Bei mir passiert das meist, wenn ich an einer Funktion arbeite, mit der ich nicht vertraut bin. Ich lege einen Branch an und mache ein paar Commits. Wenn ich nicht weiterkomme, bitte ich eine Kollegin oder einen Kollegen um Hilfe. Sie oder er startet von einem früheren Commit (vor meinem Fehler), löst das Problem und pusht die Änderungen. Jetzt muss ich meine lokale Version durch die aktualisierte Remote-Version ersetzen und meine lokalen Änderungen verwerfen, damit ich an der Funktion weiterarbeiten kann.
Ein weiteres Beispiel: Es gibt einen Konflikt, und es ist aufwendiger, den Konflikt zu beheben, als die eigenen Änderungen auf Basis der neuesten Codeversion noch einmal umzusetzen.
Egal aus welchem Grund: Stell immer sicher, dass diese Änderungen wirklich nicht benötigt werden und gefahrlos gelöscht werden können – oder sichere deinen Branch, um keinen wichtigen Stand zu verlieren.
Lokale Änderungen korrekt überschreiben
Der erste Schritt ist, die neuesten Inhalte aus dem Remote-Repository auf unseren Rechner zu holen. Das geht mit dem fetch-Befehl von Git:
git fetch
Standardmäßig werden die Inhalte des aktuellen Branches geholt – das reicht in der Regel aus. Optional können wir einen Branch angeben, den wir herunterladen möchten (ersetze unten <branch_name> durch den gewünschten Branchnamen):
git fetch origin/<branch_name>
Alternativ können wir mit der Option --all alles herunterladen:
git fetch –all
Das Holen der Änderungen aus dem Remote-Repository verändert deine Dateien im aktuellen Arbeitsverzeichnis nicht. Der Befehl fetch lädt die Änderungen herunter, führt aber keinen Merge durch. Das lokale Repository behält eine Sicht auf lokale und auf Remote-Dateien; fetch aktualisiert die Remote-Sicht.
Nach dem Herunterladen der Änderungen können wir mit dem Git-Befehl reset den aktuellen Arbeitsbranch auf einen bestimmten Stand zurücksetzen:
git reset --hard origin/<branch_name>
Die Option --hard ist nötig, damit die lokalen Änderungen von den Remote-Änderungen überschrieben werden. Im obigen Befehl ersetzen wir den aktuellen Arbeitsbranch durch origin/<banch_name>, also die soeben geholte Remote-Version dieses Branches.
Der Befehl git reset löscht lokale Änderungen – auch wenn sie bereits committet wurden. Deshalb empfiehlt es sich, vorab eine lokale Sicherung des aktuellen Branches anzulegen. Das geht so:
git branch <name_of_the_backup_branck>
Ersetze <name_of_the_backup_branch> durch den gewünschten Namen für den Backup-Branch.
Kombiniert sieht der Ablauf so aus, um alle lokalen Änderungen eines Branches durch die neueste Remote-Version zu ersetzen:
git fetch
git branch <name_of_the_backup_branch>
git reset --hard origin/<branch_name>
Wenn du dein Wissen zur Arbeit mit Branches in Git vertiefen möchtest, schau dir das Tutorial Git: Einen bestimmten Branch klonen an.
Vollständige Bereinigung durch Löschen untracked Dateien
Git fasst untracked Dateien (Dateien, die nie per git add verfolgt wurden) nicht an. Wenn wir auch diese Dateien löschen möchten, geht das mit:
git clean -fdx
Das ist ein gefährlicher Befehl, der untracked Dateien aus dem Arbeitsverzeichnis entfernt. Unbedingt mit Vorsicht verwenden: Diese Dateien werden dauerhaft gelöscht und lassen sich über Git nicht wiederherstellen. Erklärung der Optionen:
-f: Erzwingt die Ausführung. Ohne diese Sicherungsmaßnahme verweigert Git das Löschen untracked Dateien, um versehentlichen Datenverlust zu verhindern.-d: Weistgit cleanan, neben untracked Dateien auch untracked Verzeichnisse zu entfernen. Standardmäßig berücksichtigtgit cleannur Dateien.-x: Standardmäßig respektiertgit cleandie Regeln in.gitignoreund entfernt üblicherweise ignorierte Dateien/Ordner nicht. Mit -x wird dieses Verhalten aufgehoben, sodass auch durch.gitignore(oder andere Ignore-Regeln) ignorierte Dateien/Verzeichnisse gelöscht werden. Ergebnis: eine sehr gründliche Bereinigung, inklusive Build-Artefakten, Logfiles und anderen generierten Dateien.
Git Pull verstehen
Üblicherweise aktualisieren wir unser lokales Repository mit den Remote-Änderungen über den Befehl git pull. Dieser Befehl ist jedoch ungeeignet, um lokale Änderungen zu überschreiben, da git pull versucht, die lokale Version mit der Remote-Version zu mergen.
Unter der Haube führt git pull Folgendes aus:
git fetch, um die neueste Remote-Version herunterzuladen.git merge, um lokale und Remote-Branches zusammenzuführen.
Wegen dieses Merge-Schritts ist git pull ungeeignet, wenn wir lokale Änderungen ignorieren und verwerfen möchten.

Wie sieht es mit git pull --force aus?
Ein Blick in die Dokumentation zu git pull zeigt eine Option --force. Häufig wird fälschlicherweise angenommen, diese Option zwinge git pull dazu, lokale Änderungen durch Remote-Änderungen zu ersetzen.
Wenn wir --force an git pull übergeben, wird diese Option an git fetch durchgereicht. git pull --force führt also Folgendes aus:
git fetch --forcegit merge

Wir haben gelernt: fetch aktualisiert die lokale Sicht auf das Remote-Repository. Besteht der einzige Unterschied zwischen deinem lokalen Repository und dem Remote-Repository darin, dass lokale Commits fehlen (der lokale Branch ist hinter der Remote-Version zurück), aktualisiert git fetch die lokale Sicht einfach, indem diese neuen Commits der Historie hinzugefügt werden.

Es kann jedoch sein, dass jemand die Commit-Historie des Remote-Branches umgeschrieben hat, sodass sie nicht mehr zur lokalen Sicht passt. In diesem Fall schlägt fetch fehl.

Das lässt sich mit der Option --force umgehen, die Git zwingt, die lokale Historie zu ignorieren und sie mit der Remote-Historie zu überschreiben.
Wir sehen: Die Option --force bezieht sich auf das erzwungene Überschreiben der Commit-Historie und hat nichts damit zu tun, lokale Änderungen im Arbeitsverzeichnis zu ignorieren.
Lokale Änderungen integrieren
Das Überschreiben lokaler Änderungen mit den Remote-Änderungen ist keine gängige Git-Praxis, kann in bestimmten Fällen aber hilfreich sein – etwa wenn wir keine Konflikte lösen möchten oder uns die lokalen Änderungen nicht wichtig sind.
Mergen
Üblicherweise zieht man die Änderungen und löst etwaige Konflikte. Viele scheuen sich davor, Konflikte zu bearbeiten. Manche Konflikte sind mühsam, aber oft halb so wild. Ein Konflikt tritt auf, wenn:
- Sowohl im lokalen als auch im Remote-Branch dieselbe Stelle einer Datei geändert wurde.
- Eine Datei auf der einen Seite gelöscht und auf der anderen geändert wurde.
In solchen Fällen kann Git nicht erraten, welche Änderungen wir behalten wollen, und wir müssen das manuell entscheiden. Git markiert den Konflikt in den Dateien so:

Um einen Konflikt zu lösen, bearbeiten wir die Datei, entfernen die Markierungen und behalten die gewünschten Zeilen. Nachdem alle Konflikte gelöst sind, können wir die Änderungen commiten. Eine ausführliche Anleitung findest du in diesem Tutorial zum Lösen von Merge-Konflikten in Git.
Cherry-picking
Wenn wir unsere lokale Version zuerst an die Remote-Version angleichen und unsere Änderungen anschließend gezielt integrieren wollen, können wir die Commits aus dem Backup-Branch in den aktuellen Branch holen, so:
git cherry-pick <commit_hash>
Dabei ist <commit_hash> der Hash des Commits, den wir übernehmen möchten. Das setzt voraus, dass wir vor dem git reset mit git branch <name_of_the_backup_branck> einen Backup-Branch erstellt haben und die lokalen Änderungen committet waren.
Den <commit_hash> finden wir, indem wir die Commits im Backup-Branch auflisten:
git log <name_of_the_backup_branck>
Stashing
Wenn wir unsere Änderungen nicht committen oder keinen Backup-Branch erstellen möchten, können wir sie vor dem Mergen auch zwischenlagern (stashen):
git stash
Dieser Befehl speichert die aktuellen Änderungen temporär, ohne sie in die Branch-Historie zu committen. So bekommst du ein sauberes Arbeitsverzeichnis.
Nach dem Reset können wir die Änderungen mit folgendem Befehl zurückholen:
git stash pop
Mit Stashing sieht der gesamte Ablauf so aus:
git fetch
git stash
git reset --hard origin/<branch_name>
git stash pop
Mehr dazu findest du in diesem Cheat Sheet mit Stash und weiteren Git-Befehlen.
Fazit
Auch wenn es nicht der Best Practice entspricht, gibt es Situationen, in denen wir unseren lokalen Branch einfach an den Inhalt des Remote-Branches anpassen und dabei lokale Änderungen verwerfen möchten.
Oft wird fälschlicherweise angenommen, das gehe mit git pull --force. Das stimmt nicht, denn git pull --force kombiniert git fetch --force und git merge. Es versucht also, lokale und Remote-Änderungen zusammenzuführen – nicht, sie zu überschreiben.
Der korrekte Weg, lokale Änderungen mit dem Inhalt des Remote-Repositories zu überschreiben, ist:
git fetch
git reset --hard origin/<branch_name>
Mit git reset ist Vorsicht geboten: Der Befehl löscht lokale Änderungen, auch wenn sie bereits committet wurden. Hatten wir lokale Commits und einen Backup-Branch angelegt, können wir sie per git cherry-pick zurückholen. Wenn wir nicht committet haben und die lokale Arbeit nur temporär sichern möchten, nutzen wir vor dem Reset git stash und danach git stash pop, um die Änderungen zurückzubringen.
Lass dich für deine Traumrolle als Data Engineer zertifizieren
Unsere Zertifizierungsprogramme helfen dir, dich von anderen abzuheben und potenziellen Arbeitgebern zu beweisen, dass deine Fähigkeiten für den Job geeignet sind.

