Vincent Driessen: 成功したGit分岐モデル変換この記事では、過去1年間、すべてのプロジェクト(作業およびプライベートの両方)で使用してきた開発モデルを紹介します。 長い間、私は彼女について書くつもりでしたが、まだ自由な時間を見つけていません。 プロジェクトのすべての詳細については説明しません。分岐およびリリース管理戦略についてのみ触れます。

すべてのソースコードのバージョン管理ツールとして
Gitを使用します。
なぜgitなのか?
集中型バージョン管理システムと比較したGitのすべての長所と短所の詳細については
、世界規模の ネットワークを 参照 して ください 。 そこには、このトピックに関する十分な数の論争があります。 個人的に、開発者として、私は現在、他のすべてのツールよりもGitを好みます。 Gitは、開発者の態度をマージと分岐のプロセスに変えることができました。 私が来た古典的なCVS / Subversionの世界では、分岐とマージは通常危険と見なされ(「マージの競合に注意してください、痛いほど噛み付きます!」)、したがって、可能な限り実行されません。
しかし、Gitを使用すると、これらのアクティビティは非常にシンプルかつ安価になり、実際、通常の
日常のワークフローの中心になります。 比較してください:CVS / Subversionの
本では、分岐とマージは通常、最後の章(上級ユーザー向け)で説明されていますが、
Gitに関する 本では、すでに3番目の章(基本)で説明されています。
単純さと予測可能性により、分岐とマージは注意すべきアクションではなくなりました。 バージョン管理ツールは、他のどの製品よりも分岐およびマージを支援できるようになりました。
しかし、ツールについて話すのはやめて、開発モデルに移りましょう。 私が紹介したいモデルは、実際には、各チームメンバーが一緒に開発プロセスの高い管理性を実現できるように実行する一連の手順です。
分散化されているが集中化されている
提案されている分岐モデルは、1つの中央の「真の」リポジトリを含むプロジェクト構成に依存しています。 このリポジトリは中心
と見なされるだけであることに注意してください(GitはDVCSであるため、技術レベルではメインリポジトリのようなものはありません)。 このリポジトリを用語オリジンと呼びます。 この名前は、すべてのGitユーザーにすでによく知られています。

各開発者は、変更を取得し、オリジンに公開します(プル&プッシュ)。 しかし、一元化されたプッシュプル関係に加えて、各開発者は自分のマイクロチーム内の他の同僚からの変更をピックアップすることもできます。 たとえば、この方法は、2人以上の開発者が大きな新機能で共同作業している場合に便利ですが、事前に不完全な作品を元に公開することはできません。 上の写真は、アリスとボブ、アリスとデビッド、クレアとデビッドのサブグループを示しています。
技術的には、これは簡単です。アリスはボブのリポジトリを指すボブと呼ばれるリモートGitブランチを作成し、ボブは彼女のリポジトリで同じことを行います。
主な支店

開発モデルの中核は、既存のほとんどのモデルと変わりません。 中央リポジトリには、常に存在する2つのメインブランチが含まれています。
マスターブランチは、リポジトリが初期化されるときに作成されます。これは、すべてのGitユーザーに馴染みがあるはずです。 彼女と並行して、developという開発ブランチも作成します。
オリジン/マスターブランチをメインと見なします。 つまり、その中のソースコードは、いつでも任意の時点で
本番環境に対応している必要があります。
オリジン/開発ブランチは、開発のメインブランチと見なされます。 いつでもそこに保存されるコードには、次のリリースに必要な公開された最新の変更が含まれている必要があります。 このブランチは「統合」とも呼ばれます。 自動ナイトビルドのアセンブリのソースとして機能します。
開発ブランチ(開発)のソースコードが安定状態になり、リリースの準備ができたら、すべての変更を特定の方法でメインブランチ(マスター)に注ぎ、リリース番号でタグ付けする必要があります。 以下では、このプロセスを詳細に検討します。
したがって、変更がメインブランチ(マスター)にマージされるたびに
、定義により 、新しいリリースが取得
されます 。 私たちはこのルールを非常に厳しくしようとしているので、原則として、Gitフックを使用して製品を自動的に収集し、メインブランチ(マスター)にコミットするたびに製品サーバーに配置できます。
補助枝
masterおよびdevelopmentのメインブランチに加えて、開発モデルには、チームメンバー間の開発の並列化、新機能の実装の簡素化、リリースの準備、およびアプリケーションの製品バージョンの問題の迅速な修正に使用されるいくつかのタイプの補助ブランチが含まれています。 メインブランチとは異なり、これらのブランチの寿命は常に制限されています。 それらのそれぞれは最終的に遅かれ早かれ去ります。
次の種類のブランチを使用します。
各タイプのブランチには、固有の目的と厳格なルールセットがあり、そこからブランチを生成でき、そこにマージする必要があります。 次に、それらを順番に検討します。
もちろん、技術的な観点からは、これらのブランチには「特定の」ものはありません。 カテゴリへのブランチの分割は、それらの使用方法の観点からのみ存在します。 そして、他のすべてはGitの古き良きブランチです。
機能ブランチ

生成元:開発
流れ込む必要がある:開発
命名規則:master、develop、release- *またはHotfix- *を除くすべて
機能ブランチは、トピックブランチとも呼ばれ、現在または将来のリリースで表示される新しい機能を開発するために使用されます。 機能(機能)の作業の開始時点では、どの特定のリリースに追加されるのかまだ不明な場合があります。 機能ブランチの存在の意味は、この機能(機能)の開発が継続している限り存続するということです。 ブランチでの作業が完了すると、後者はメインの開発ブランチにマージされ(機能が今後のリリースに追加されることを意味します)、削除されます(実験が失敗した場合)。
機能ブランチは通常、開発者リポジトリに存在しますが、メインリポジトリ(オリジン)には存在しません。
機能ブランチの作成
新しい機能の作業を開始すると、開発ブランチからブランチが作成されます。
$ git checkout -b myfeature develop
Switched to a new branch "myfeature"
開発する完全な機能を追加する
完成した機能(機能)は、developブランチにマージされ、次のリリースに入ります。
$ git checkout develop
Switched to branch 'develop'
$ git merge --no-ff myfeature
Updating ea1b82a..05e9557
( )
$ git branch -d myfeature
Deleted branch myfeature (was 05e9557).
$ git push origin develop
--no-ffフラグを指定すると、Gitは、マージが高速転送アルゴリズムを使用して実行できる場合でも、マージ中に常に新しいコミットオブジェクトを作成します。 これにより、ブランチが存在したという情報を失わずに、行われたすべての変更をグループ化できます。 比較する:

2番目のケースでは、変更履歴で特定のコミットオブジェクトが一緒に機能を形成することを確認することはできません。このため、コミット内のすべてのメッセージを手動で読み取る必要があります。 この場合、頭痛なしに機能全体(つまり、コミットのグループ)をキャンセルすることは不可能であり、-no-ffフラグを使用するとこれは基本的に行われます。
もちろん、このアプローチは追加の(空の)コミットオブジェクトを作成しますが、結果として得られる利点は、そのような価格を正当化する以上のものです。
残念ながら、Gitを設定して、-no-ffがデフォルトのマージ動作になるようにする方法をまだ見つけていません。 ただし、このメソッドを実装する必要があります。
リリースブランチ
生成元:開発
流れ込む必要がある:開発とマスター
命名規則:release- *
リリースブランチは、製品の新しいバージョンのリリースの準備に使用されます。 新しいバージョンのリリース前に、iに最終ポイントを置くことができます。 さらに、次のリリースのメタデータ(バージョン番号、ビルド日付など)と同様に、マイナーな修正をそれらに追加できます。 このすべての作業がリリースブランチに送信されると、メインの開発ブランチがクリーンアップされ、さらなる機能が追加されます(これは次の大きなリリースに含まれます)。
開発ブランチの状態が新しいリリースに対応する要件を完全またはほぼ完全に満たした時点で、新しいリリースブランチを生成する必要があります。 少なくとも、このリリースに必要なすべての機能はすでに開発ブランチに組み込まれています。 次のリリース向けの機能は注入されない可能性があります。 これらの機能のブランチが、現在のリリースブランチが開発ブランチから切り離されるまで待機する場合はさらに優れています。
次のリリースでは、新しいブランチが作成された時点でのみバージョン番号が取得されますが、以前のバージョンでは取得されません。 この時点まで、開発ブランチには「新しいリリース」の変更が含まれていますが、リリースブランチが分離されるまで、このリリースにバージョン0.3、1.0、または他のバージョンがあるかどうかはわかりません。 この決定は、新しいリリースブランチを作成するときに行われ、プロジェクトで採用されているプロジェクトバージョン番号付け規則によって決まります。
リリースブランチを作成する
リリースブランチは、開発ブランチから作成されます。 たとえば、現在リリースされているリリースにバージョン1.1.5があり、途中で変更が加えられた新しいビッグリリースがあるとします。 開発ブランチは「次のリリース」の準備ができており、このリリースにはバージョン1.1.6(2.0ではなく)が含まれると判断しています。 この場合、新しいブランチを作成し、プロジェクトの新しいバージョンに対応する名前を付けます。
$ git checkout -b release-1.2 develop
Switched to a new branch "release-1.2"
$ ./bump-version.sh 1.2
Files modified successfully, version bumped to 1.2.
$ git commit -a -m "Bumped version number to 1.2"
[release-1.2 74d9424] Bumped version number to 1.2
1 files changed, 1 insertions(+), 1 deletions(-)
新しいブランチを作成し、それに切り替えてから、バージョン番号(バンプバージョン番号)を設定しました。 この例では、bump-version.shは架空のスクリプトであり、作業コピーの一部のファイルに新しいバージョンを書き込むことでファイルを変更します。 (もちろん、これらの変更を手動で行うこともできます。
一部のファイルが変更されていることに注意してください。)その後、プロジェクトの新しいバージョンをコミットします。
この新しいブランチは、新しいリリースのリリースの準備が整うまでしばらく存在する可能性があります。 この間に、発見されたバグの修正をこのブランチに追加できます(開発用ではありません)。 ただし、このブランチに大きな新しい変更を追加することは固く禁じられています。 彼らは常に開発ブランチに流れ込み、次の大きなリリースを待つべきです。
リリースブランチを閉じる
リリースブランチが最終的にリリースの準備ができたと判断したら、いくつかのことをする必要があります。 まず、リリースブランチがメインブランチにマージされます(マスターの各コミットは、当然のこと
ながら、新しいリリースです)。 次に、マスターのこのコミットにタグを付けて、後で製品の既存のバージョンに簡単にアクセスできるようにする必要があります。 最後に、将来のリリースにもバグ修正が含まれるように、リリースブランチに加えられた変更を開発ブランチ(開発ブランチ)に追加し直す必要があります。
Gitの最初の2つのステップ:
$ git checkout master
Switched to branch 'master'
$ git merge --no-ff release-1.2
Merge made by recursive.
( )
$ git tag -a 1.2
これでリリースが公開され、タグ付けされました。
注 :必要に応じて、-sまたは-u <key>フラグを使用して、タグに暗号的に署名することもできます。
将来のリリースで変更を保存するには、これらの変更を開発に組み込む必要があります。 このようにします:
$ git checkout develop
Switched to branch 'develop'
$ git merge --no-ff release-1.2
Merge made by recursive.
( )
このステップは、原則として、合併の競合につながる可能性があります(競合の原因がプロジェクトのバージョン番号の変更であることがよくあります)。 これが発生した場合は、修正してコミットを発行してください。
これでついにリリースブランチが完成しました。 不要になったため、削除できます。
$ git branch -d release-1.2
Deleted branch release-1.2 (was ff452fe).
修正プログラムの枝

生成元:マスター
流れ込む必要がある:開発とマスター
命名規則:ホットフィックス-*
修正プログラムのブランチは、計画外でない限り、新しい製品リリースの準備にも使用されるため、リリースブランチと非常によく似ています。 これらは、製品の製品バージョンの望ましくない動作をすぐに修正する必要があるために発生します。 すぐに修正する必要があるプロダクションバージョンでバグが見つかった場合、マスターブランチが修正に取り組むために、対応するマスターバージョンタグから新しいブランチが生成されます。
その存在の意味は、開発版ブランチでのチームの作業は静かに続けられる一方、実稼働版のクイックフィックスを準備しているということです。
ホットフィックスブランチの作成
修正プログラムのブランチは、マスターブランチから作成されます。 たとえば、現在の製品リリースにバージョン1.2があり、その中に(突然!)重大なバグが検出されたとします。 また、開発ブランチ(開発)の変更は、新しいリリースで公開するほど安定していません。 ただし、新しいパッチブランチを作成して、問題の解決に取り組み始めることができます。
$ git checkout -b hotfix-1.2.1 master
Switched to a new branch "hotfix-1.2.1"
$ ./bump-version.sh 1.2.1
Files modified successfully, version bumped to 1.2.1.
$ git commit -a -m "Bumped version number to 1.2.1"
[hotfix-1.2.1 41e61bb] Bumped version number to 1.2.1
1 files changed, 1 insertions(+), 1 deletions(-)
ブランチを作成した後、必ずバージョン番号を更新してください!
これで、バグを修正し、少なくとも1回、少なくとも数回のコミットで変更を公開できます。
$ git commit -m "Fixed severe production problem"
[hotfix-1.2.1 abbe5d6] Fixed severe production problem
5 files changed, 32 insertions(+), 17 deletions(-)
パッチブランチを閉じる
バグが修正されたら、変更をメインブランチ(マスター)と開発ブランチ(開発)に戻して、この修正が次のリリースで確実に反映されるようにする必要があります。 これは、リリースブランチが閉じられる方法に非常に似ています。
まず、メインブランチ(マスター)を更新し、新しいバージョンにタグをタグ付けする必要があります。
$ git checkout master
Switched to branch 'master'
$ git merge --no-ff hotfix-1.2.1
Merge made by recursive.
( )
$ git tag -a 1.2.1
注 :必要に応じて、-sまたは-u <key>フラグを使用して、タグに暗号的に署名することもできます。
次のステップは、修正を開発ブランチに転送することです。
$ git checkout develop
Switched to branch 'develop'
$ git merge --no-ff hotfix-1.2.1
Merge made by recursive.
( )
このルールには1つの例外があります。
現時点でリリースブランチがある場合、ホットフィックスブランチは、開発ブランチではなく、それにマージする必要があります 。 この場合、修正はリリースブランチが閉じられると、リリースブランチ全体とともに開発ブランチに送られます。 (開発での作業に即時のバグ修正が必要で、現在のリリースが完了するのを待つことができない場合でも、バグ修正を開発ブランチにパッチすることができ、完全に安全です)。
最後に、一時ブランチを削除します。
$ git branch -d hotfix-1.2.1
Deleted branch hotfix-1.2.1 (was abbe5d6).
おわりに
この分岐モデルには根本的に新しいものはまったくありませんが、この記事が始まる「全体像」は、最良の側面からのプロジェクトで証明されています。 エレガントなメンタルモデルを形成します。一目で簡単に完全に把握でき、プロジェクトに作用する分岐およびマージプロセスについてチームが共同で理解することができます。
この画像の高品質PDFバージョンは、
ここから無料でダウンロードでき
ます 。 いつでもアクセスできるように、印刷して壁に掛けてください。
ご注意 翻訳者:記事は新しいものではなく、オリジナルへのリンクがすでにハブに表示されています この翻訳は、まだ英語がそれほど簡単ではない人のためのものです(私がプロパガンダに携わっている私の同僚のためだけでなく、へへ)。 この記事で説明されている手順を自動化するために、著者はgithubにあるgitflowプロジェクトを作成しました 。