Wenn ein git merge conflict auf dem Bildschirm erscheint, ist die erste Reaktion vieler Entwickler Panik — dabei ist ein Konflikt eigentlich Git's Art, dir zu helfen. Git stellt fest, dass dieselben Zeilen auf zwei Branches unterschiedlich geändert wurden, und kann nicht entscheiden, welche Version richtig ist. Also hält es an und gibt die Entscheidung an dich zurück. Diese Anleitung erklärt Schritt für Schritt, warum Konflikte entstehen, wie du die Marker im Terminal liest und wie du die Datei sicher bereinigst.
Was ist ein Merge-Konflikt genau?
Git führt Änderungen Zeile für Zeile zusammen. Wenn zwei Branches unterschiedliche Bereiche derselben Datei berühren, kombiniert Git sie problemlos. Ein Konflikt entsteht nur, wenn dieselben Zeilen (oder eng beieinanderliegende Zeilen) auf beiden Branches unterschiedlich bearbeitet wurden, oder wenn eine Seite löscht, was die andere geändert hat. Dann fragt Git: „Hier gibt es zwei mögliche Wahrheiten, welche willst du?"
Konflikte können bei fast all diesen Befehlen auftreten: git merge, git rebase, git pull (das intern einen Merge oder Rebase ausführt), git cherry-pick und git stash pop. Der Mechanismus ist überall gleich — wenn du einen lösen kannst, kannst du sie alle lösen.
Den Konflikt lesen: was die Marker bedeuten
Wenn du eine Datei mit Konflikt öffnest, siehst du drei von Git eingefügte Marker:
<<<<<<< HEAD
const timeout = 5000;
=======
const timeout = 10000;
>>>>>>> feature/login
- Zwischen
<<<<<<< HEADund=======: deine Seite (der Branch, auf dem du bist, „ours"). - Zwischen
=======und>>>>>>>: die eingehende Seite, der Branch, den du zusammenführst („theirs"). - Das Label am Ende (
feature/login) sagt dir, woher die konfliktierende Änderung stammt.
Ein wichtiges Detail: Während eines rebase ist die Bedeutung von „ours" und „theirs" umgekehrt, weil Rebase deine Commits oben auf den Ziel-Branch neu abspielt. Also steht HEAD für den Ziel-Branch und der untere Block enthält deine Änderung. Denk daran, wenn du über die Kommandozeile löst.
Schrittweise Lösung
Hier ist ein sicherer, wiederholbarer Ablauf:
- Den Zustand ansehen. Führe
git statusaus; es listet die konfliktierenden Dateien unter der Überschrift „Unmerged paths" auf. - Jede konfliktierende Datei öffnen. Finde jeden Marker-Block. Du hast drei Möglichkeiten: deine Seite behalten, die eingehende Seite behalten, oder beide von Hand zusammenführen.
- Das richtige Ergebnis schreiben. Du musst die drei Marker-Zeilen (
<<<<<<<,=======,>>>>>>>) löschen, sodass nur der gewünschte Endcode übrig bleibt. - Als gelöst markieren. Stage die Datei mit
git add <datei>. - Den Vorgang abschließen. Fahre fort mit
git commitbei einem Merge,git rebase --continuebei einem Rebase odergit cherry-pick --continuebei einem Cherry-Pick.
Editor-Unterstützung macht es deutlich einfacher. VS Code hebt konfliktierende Blöcke hervor und zeigt die Schaltflächen „Accept Current Change / Accept Incoming Change / Accept Both Changes". Prüfe trotzdem vor dem Klick, ob das Ergebnis wirklich sinnvoll ist — automatisches Übernehmen liefert nicht immer den richtigen Code.
Schnelle Entscheidungen über die Kommandozeile
Manchmal weißt du, dass du eine ganze Seite einer Datei von oben bis unten willst. Statt von Hand zu bearbeiten:
# für diese Datei komplett die Version meines Branches behalten
git checkout --ours config/app.php
# für diese Datei komplett die Version des eingehenden Branches behalten
git checkout --theirs config/app.php
# danach stagen
git add config/app.php
Willst du vollständig zum Punkt vor dem Konflikt zurück, bringt dich git merge --abort (oder git rebase --abort bei einem Rebase) in den Ausgangszustand zurück. Das ist der sauberste Weg, neu anzufangen, ohne etwas kaputtzumachen.
Konflikte von vornherein reduzieren
Der beste Konflikt ist der, der nie passiert. Ein paar Gewohnheiten senken das Risiko spürbar:
- Klein und oft committen, häufig integrieren. Einen Branch wochenlang von main fernzuhalten lädt dazu ein, dass sich Konflikte stapeln. Bleib aktuell mit
git pull --rebase. - Dateien klein und fokussiert halten. Eine modulare Struktur statt riesiger Einzeldateien verringert die Wahrscheinlichkeit, dass zwei Personen dieselbe Zeile berühren.
- Auf generierte Dateien achten. Lock-Dateien wie
composer.lockundpackage-lock.jsonkollidieren oft; sie neu zu generieren (z. B.composer install) ist sicherer als das Bearbeiten von Hand. - Formatierung standardisieren. Ein gemeinsamer Formatter im Team (Prettier, PHP-CS-Fixer) eliminiert Scheinkonflikte, die nur durch Einrückung oder Leerzeichen entstehen.
Deine Lösung überprüfen
Nach dem Schließen eines Konflikts reicht „kompiliert es" nicht aus. Stelle sicher, dass beide Seiten der zusammengeführten Änderung ihre Absicht behalten haben: führe die Tests aus, öffne die App und teste manuell das Verhalten, das mit dem Konfliktbereich zusammenhängt. Den Endzustand vor dem Commit noch einmal mit git diff durchzusehen ist ein schneller Weg, eine vergessene >>>>>>>-Zeile oder alten Code, der hätte gelöscht werden sollen, zu erwischen.
Häufige Fragen
Ich habe beim Auflösen die falsche Seite behalten — kann ich das rückgängig machen?
Wenn du noch nicht committet hast, bricht git merge --abort den ganzen Merge ab, sodass du neu anfangen kannst. Hast du bereits committet, finde mit git reflog den vorherigen HEAD und kehre mit git reset --hard <hash> dorthin zurück. Genau deshalb solltest du nicht pushen, bevor du deine Lösung überprüft hast.
Ich löse immer wieder dieselben Konflikte — gibt es eine Lösung?
Ja. Aktiviere rerere (reuse recorded resolution) mit git config --global rerere.enabled true. Git merkt sich, wie du einen Konflikt gelöst hast, und wendet es automatisch erneut an, wenn derselbe wieder auftaucht — bei langen Rebases extrem nützlich.
Warum unterscheiden sich „ours" und „theirs" zwischen Merge und Rebase?
Bei einem Merge ist der Branch, auf dem du bist, „ours". Bei einem Rebase nimmt Git zuerst den Ziel-Branch als Basis und spielt deine Commits darüber ab, sodass sich die Rollen vertauschen: HEAD steht für den Ziel-Branch und „theirs" ist deine abgespielte Änderung. Prüfe, in welchem Befehl du bist, bevor du entscheidest.
Bremsen Konflikte dein Projekt? Wir können deinen Git-Workflow, deine Branching-Strategie und deinen Deployment-Prozess gemeinsam optimieren. Wenn du Hilfe bei deinem Projekt möchtest, nimm Kontakt mit mir auf.