Feature-Branches

Die Grundidee hinter Workflows mit Feature-Branches ist, dass die Entwicklung einzelner Features jeweils in einem dedizierten Branch und nicht im main-Branch stattfindet. Diese Kapselung erleichtert in einem Entwicklungsteam die Arbeit, da Veränderungen im main-Branch nicht stören und zunächst vernachlässigt werden können. Umgekehrt sollte so vermieden werden, dass der main-Branch durch unfertigen Code verunreinigt wird. Dieses zweite Argument erleichtert dann auch die kontinuierliche Integration mit anderen Komponenten.

Siehe auch

Merge- oder Pull-Requests

Die Kapselung der Entwicklung einzelner Features in einem Branch ermöglicht zudem die Verwendung von sog. Merge- oder Pull-Requests um Änderungen mit anderen im Team diskutieren zu können und ihnen die Möglichkeit zu geben, ein Feature freizugeben, bevor es in das offizielle Projekt integriert wird. Wenn ihr in eurer Feature-Entwicklung auf Probleme stoßt, könnt ihr Merge- oder Pull-Requests jedoch auch nutzen um mit anderen im Team Lösungsmöglichkeiten zu erörtern.

Merge- oder Pull-Requests werden von Web-basierten Diensten wie GitHub, GitLab und Atlassian zum Review und Kommentieren der Änderungen bereitgestellt. Mit @ID in euren Kommentaren könnt ihr auch bestimmte Personen aus dem Projektteam direkt um Feedback bitten. Sofern ihr automatisiert testet, könnt ihr hier auch die Testergebnisse sehen; evtl. entspricht ja der Coding Style nicht euren Projektrichtlinien, oder die Testabdeckung ist ungenügend. In den Merge- oder Pull-Requests werden solche Diskussionen gefördert und dokumentiert ohne dass sie als unmittelbar als Commits im Repository erscheinen.

Warnung

Merge- oder Pull-Requests sind kein Bestandteil von Git selbst, sondern des jeweiligen Web-basierten Dienstes. Sie sind auch nicht standardisiert, sodass sie beim Wechsel auf einen anderen Dienst nur mühsam übernommen werden können.

GitHub Flow

GitHub Flow ist ein einfacher Workflow, bei dem es neben dem main-Branch nur verschiedene Feature-Branches geben sollte. Der Lebenszyklus eines Feature-Branches könnte dann so aussehen:

  1. Alle Feature-Branches starten auf Basis des aktuellen main-Branches.

    Hierzu wechseln wir zunächst in den main-Branch, holen uns die neuesten Änderungen vom Server und aktualisieren unsere lokale Kopie des Repositories:

    $ git switch main
    $ git fetch origin
    $ git reset --hard origin/main
    
  2. Erstellen des Feature-Branches.

    Wir erstellen einen Feature-Branch mit git switch -c und der Nummer des Tickets in der Aufgabenverwaltung, das dieses Feature beschreibt.

    $ git switch -c 17-some-feature
    
  3. Hinzufügen und Committen von Änderungen.

    $ git add SOMEFILE
    $ git commit
    
  4. Pushen des Feature-Branches mit den Änderungen.

    Durch das Pushen des Feature-Branches mit Deinen Änderungen erstellt Ihr nicht nur eine Sicherungskopie eurer Änderungen, sondern ihr ermöglicht auch anderen im Team, sich die Änderungen anzuschauen.

    $ git push -u origin 17-some-feature
    

    Der -u-Parameter fügt den 17-some-feature-Branch dem Upstream-Git-Server (origin) als Remote-Branch hinzu. Zukünftig könnt ihr dann in diesen Branch pushen ohne weitere Parameter angeben zu müssen.

  5. Merge- oder Pull-Request stellen

    Sobald ihr ein Feature fertiggestellt habt, wird dieses nicht sofort in den main-Branch gemergt, sondern ein Merge- oder Pull-Request erstellt, durch den andere aus dem Entwicklungsteam die Gelegenheit erhalten, eure Änderungen zu überprüfen. Alle Änderungen an diesem Branch werden nun ebenfalls in diesem Merge- oder Pull-Request angezeigt.

  6. Zusammenführen

    Sobald euer Merge- oder Pull-Request akzeptiert wird, müsst ihr zunächst sicherstellen, dass euer lokaler main-Branch mit dem Upstream-main-Branch synchronisiert ist; erst dann könnt ihr den Feature-Branch in den main-Branch mergen und schließlich den aktualisierten main-Branch zurück in den Upstream-main-Branch pushen. Dies wird jedoch nicht selten zu einem Merge-Commit führen. Dennoch hat dieser Workflow den Vorteil, dass klar zwischen der Feature-Entwicklung und dem Zusammenführen unterschieden werden kann.

Simple-Git-Workflow

Auch Atlassian empfiehlt eine ähnliche Strategie, wobei sie jedoch ein rebase der Feature-Branches empfehlen. Hiermit erhaltet ihr einen linearen Verlauf, indem die Änderungen im Feature-Branch vor dem Zusammenführen mit einem Fast-Forward-Merge an die Spitze des main-Branch verschoben werden.

  1. Verwendet rebase, um euren Feature-Branch auf dem neuesten Stand von main zu halten:

    $ git fetch origin
    $ git rebase -i origin/main
    

    In dem selteneren Fall, dass andere aus dem Team auch im selben Feature-Zweig arbeiten, solltet ihr auch deren Änderungen übernehmen:

    $ git rebase -i origin/17-some-feature
    

    Löst zu diesem Zeitpunkt alle Konflikte, die sich aus rebase ergeben. Dies sollte am Ende der Feature-Entwicklung zu einer Reihe von sauberen Merges geführt haben. Außerdem bleibt die Historie eurer Feature-Zweige sauber und fokussiert, ohne störendes Rauschen.

  2. Wenn ihr bereit für Feedback seid, pusht euren Zweig:

    $ git push -u origin 17-some-feature
    

    Anschließend könnt ihr einen Merge- oder Pull-Request stellen.

    Nach diesem Push könnt ihr als Reaktion auf Feedback den entfernten Zweig immer wieder aktualisieren.

  3. Nachdem die Überprüfung abgeschlossen solltet ihr eine letzte Bereinigung der Commit-Historie des Feature-Zweiges vornehmen, um unnötige Commits zu entfernen, die keine relevanten Informationen liefern.

  4. Wenn die Entwicklung abgeschlossen ist, führt die beiden Zweige mit -no-ff zusammen. Dadurch bleibt der Kontext der Arbeit erhalten und es wird einfach sein, das gesamte Feature bei Bedarf zurückzunehmen:

    $ git switch main
    $ git pull origin main
    $ git merge --no-ff 17-some-feature
    

Der Simple-Git-Workflow über rebase schafft eine strikt lineare Versionshistorie. In der linearen Historie ist es tendenziell leichter, Änderungen nachzuvollziehen und Fehler zu finden, beispielsweise über bisect.

Zusammenfassung

Die Vorteile von Feature-Branches-Workflows sind vor allem

  • Features werden in einzelnen Branches isoliert, sodass jedes Teammitglied unabhängig arbeiten kann.

  • Gleichzeitig wird die Zusammenarbeit im Team enger über Merge- oder Pull-Requests.

  • Das zu verwaltende Code-Inventar bleibt relativ klein da die Feature-Branches üblicherweise schnell in den main übernommen werden können.

  • Die Workflows entsprechen den üblichen Methoden kontinuierlicher Integration.

Sie können jedoch nicht beantworten, wie Deployments in unterschiedliche Umgebungen oder die Aufteilung in verschiedene Releases erfolgen sollen. Mögliche Antworten hierfür werden in Deployment und Release Branches beschrieben.

Siehe auch

Beide Varianten mit Feature Branches sind stark vereinfachte Alternativen des deutlich komplexeren Git Flow.