Git

今さらながらgit pull –rebase origin developについて調べた

--rebaseをつけた場合とつけない場合でどのような違いがあるかについて理解していなかったので、調べてみたのでその内容をまとめたいと思います。

前提

Mainブランチあり、そこからFeatureブランチを切って開発しているとします。そこで、他の人の変更がMainブランチに入り、自分はその変更を使いたいケースを考えます。

この場合の方法は2種類あります。一つはプルする方法、もう一つはリベースする方法です。まずはプルする方法からまとめます。

プルする方法

コマンドは簡単で、featureブランチからgit pull origin mainです。

こうすると、FeatureブランチにMainブランチの変更がまず入り、そこにFeatureブランチの変更が加えられます。コミットはそのまま使われ、また必ずマージコミットが追加されます。

文字で書いても意味不明なので、図で書くとこんな感じになります。

  1. Featureブランチのコミットがそのまま使われる
  2. 必ずマージコミットが打たれる

次にリベースする方法を見ていきます。

リベースする方法

こちらはプルするときにオプションで--rebaseを指定し、git pull --rebase origin mainとします。

こうすると、FeatureブランチにMainブランチの変更が入るところまでは一緒で、そこからFeatureブランチの変更が加えられるのですが、そのやり方に差があります。

リベースでは変更されると、そこで新しくコミットされる形をとります。コンフリクトが起こった場合はリベースの度に解消していき、結果的に下のような図の状態となります。

  1. Featureブランチのコミットとは別のコミットが打たれる
  2. マージコミットは打たれない

このような特徴があるため、リベース前の状態でリモートブランチにプッシュしてある場合、リベースをした後はコミットが書き換わるので、プッシュできなくなります。そのため、--forceオプションをつけて強制プッシュをする必要があります。

そのブランチが自分だけのものだった場合は大丈夫ですが、他の人も共用で使っている場合には大惨事になるので注意が必要な操作です。

リベースだと作業が増えるのでプルでいいやとなりがちですが、リベースの場合だと他のブランチを取り込んでもFeatureブランチのコミット履歴が汚れないため、リベース派の人も多くいる印象です。

操作ログ

実際に上のことが起きていることを確かめたログを貼っておきます。間違えて3のコミットを2回打ってしまいましたが、影響ないのでスルーでお願いしますmm

Mainブランチ
$ git log --oneline                                                                                                                    2022-09-23 15:30
f96a5f1 (HEAD -> main, origin/main) 4
97b2afe 3
6ae9a4d 3
0d054ed 2
9aa26f4 initial commit

取り込み前のFeatureブランチ
$ git log --oneline                                                                                                                  2022-09-23 15:32
590a047 (HEAD -> main) 6
bbb4f5f 5
9aa26f4 initial commit

プル後のFeatureブランチ
9fc36 (HEAD -> feature) Merge branch 'main' of github.com:shun0211/git-demo into feature
590a047 6
bbb4f5f 5
f96a5f1 4
97b2afe 3
6ae9a4d 3
0d054ed 2
9aa26f4 initial commit

リベース後のFeatureブランチ
$ git log --oneline                                                                                                                 2022-09-23 15:26
1a9747b (HEAD -> feature) 6
6f3cf43 5
f96a5f1 (origin/main, main) 4
97b2afe 3
6ae9a4d 3
0d054ed 2
9aa26f4 initial commit

プル後ではFeatureブランチのコミットが使われているのに対して、リベースでは書き換えられているのが分かりますね。また、マージコミットが打たれていないことも分かります。

まとめ

以上、今さらな内容かと思いますがまとめてみました。
分かりにくいやアドバイス等ありましたらコメントくださると幸いです。では!
Twitterもやってますので、フォローしていただけるとうれしいです。

ABOUT ME
sakai
東京在住の30歳。元々は車部品メーカーで働いていてましたが、プログラミングに興味を持ちスクールに通ってエンジニアになりました。 そこからベンチャー → メガベンチャー → 個人事業主になりました。 最近は生成 AI 関連の業務を中心にやっています。 ヒカルチャンネル(Youtube)とワンピースが大好きです!