【Git】git squash でコミットをまとめる方法を初心者向けにわかりやすく解説
はじめに
Gitはソフトウェア開発で使われるバージョン管理システムで、複数人でコードを扱う際にとても便利です。
ただ、作業を重ねるうちにコミット履歴が細かくなりすぎて見づらくなることがあります。
ここで役立つのが git squash という操作です。
複数のコミットを1つのコミットにまとめることで、履歴の整理やレビューの効率化を図ることができます。
今回は、初心者の皆さんでもわかりやすいように、具体的な事例を交えながら git squash の基礎から使い方までを解説します。
実務でもよく使われる場面を取り上げますので、実際にプロジェクトに導入するイメージを持ちやすいのではないでしょうか。
この記事を読むとわかること
- git squash の概要とメリット
- 実務でどう役立つのか
- コミットをまとめる具体的な手順
- 注意すべきポイントとエラー対応
git squash とは何か
Gitを使って開発していると、少しずつコードを修正するたびにコミットを行うことが多いです。
細かいコミットがあるのは悪いことではありませんが、開発が一段落したあとにレビューや履歴参照をするとき、コミットが多すぎて全体像をつかみにくくなる場合があります。
そこで git squash を使うと、たとえば直近の複数コミットを1つにまとめられます。
この操作を行うと、コミット履歴がスリムになり、読みやすくなるメリットがあります。
なぜコミットをまとめるのか
細分化されたコミットのままだと、履歴を追う際に以下のような不便が生じることがあります。
- 途中経過が多すぎて何をしたかわかりづらい
- Pull Requestをレビューするときにコミットが多くて確認が面倒
こうした事態を避けるために、あらかじめローカルで細かいコミットを作っておき、機能追加やバグ修正が完了した段階でコミットを一つにまとめます。
これにより、履歴をさかのぼって機能単位で理解しやすくなるのです。
実務での活用シーン
実際の開発現場では、branchを分けて新しい機能を作成し、テストしながら数多くのコミットを行うことがよくあります。
しかし、チームでコードレビューを実施するときに、無数のコミットが並んでいると全容を把握しにくいかもしれませんね。
そこで、メインブランチへ統合する前にコミットを整理する目的で git squash を使う場面があります。
たとえば、以下のようなケースが典型的です。
- 1機能に対して5回以上コミットしたが、本来は1つのコミットにまとまっていたほうが読みやすい
- 誤ってコミットメッセージを何度か修正してしまい、履歴が煩雑になっている
こうした状況なら、squashでひとまとめにすることで、レビューの負担を軽減できます。
コミット履歴をシンプルに保つことは、チーム全体の生産性にもつながります。
git squash の基本手順
ここでは、git rebase のインタラクティブモードを使った squash の流れを見ていきましょう。
squashは、特定の範囲のコミットをまとめるときに非常に便利です。
大まかな手順は以下のとおりです。
- まとめたいコミット数を把握する
- インタラクティブモードでrebaseを実行する
- エディタ上でsquashするコミットを指定する
- rebase終了後に履歴がまとまったことを確認する
では、もう少し詳しく見ていきましょう。
rebase -i の使い方
まず、ターミナルやコマンドプロンプトで git log を確認して、直近のコミットがどれだけあるかを把握します。
たとえば、直近3つのコミットを1つにまとめたい場合は、以下のコマンドを入力します。
git rebase -i HEAD~3
すると、エディタが開いて以下のような行が表示されるはずです(コミットIDやメッセージは例です)。
pick 1234567 Fix a small bug pick 89abcde Add more debug logs pick abcdef1 Update README
この行のうち、最初のコミットを "pick" のまま残し、他のコミットを "squash" に変更すると、後方のコミットが前方のコミットに統合される形になります。
pick 1234567 Fix a small bug squash 89abcde Add more debug logs squash abcdef1 Update README
編集を保存してエディタを閉じると、コミットメッセージの編集画面が表示されます。
ここで、新たにまとめられるコミットのメッセージを好きな形に整えることで、コミットログをきれいにできます。
git push --force の必要性
コミットをまとめたあとは、リモートリポジトリと履歴が食い違う可能性があります。
この場合は、force push が必要になることがあります。
たとえば、以下のようにすることで、新しい履歴をリモートに反映させることができます。
git push origin ブランチ名 --force
ただし、force push は慎重に行いましょう。
チームメンバーが同じブランチを使っているときは、履歴が書き換わることで混乱を招くことがあるからです。
git squash と merge の違い
squashはあくまでコミットをまとめる手段ですが、Gitには他にもブランチを統合する方法として merge や rebase があります。
これらはそれぞれ役割が異なるので、混同しないように注意しましょう。
merge
ブランチを統合する方法で、通常はすべてのコミット履歴を保持します。
たとえば、mainブランチに featureブランチをマージすると、featureブランチでのコミットがすべて残る状態になります。
rebase
ブランチを切り替えるように履歴を付け替える方法です。
コミットの履歴を切り取って、別のブランチの先頭に付け足すイメージになります。
squash
mergeやrebaseの流れの中で、複数のコミットをまとめるのが squash です。
他のブランチと統合しつつ、コミット履歴をきれいに整えることができるのが特徴です。
注意すべきポイント
実務で git squash を扱うときには、いくつか留意しておくべき点があります。
1つ目は、共同作業中のブランチでは安易にrebaseやsquashをしない ことです。
他のメンバーが同じブランチをチェックアウトして作業していると、コミット履歴が大幅に変わってしまうため、競合や混乱が起きやすいのです。
2つ目は、コミットメッセージの粒度を意識する ことです。
まとめすぎると変更内容の追跡が難しくなる場合もあります。
ある程度まとめた方がよい場面と、細かく残しておいた方がよい場面を見極めるのが大切です。
チームで作業しているブランチを force push すると、他の人のローカルリポジトリと履歴が食い違う原因になります。
慎重に扱うようにしましょう。
トラブルシューティング
コミットをまとめたあと、rebaseの途中で競合が発生することがあります。
これは、通常の競合解決と同じ手順で対処できますが、初心者の方は少し戸惑うかもしれません。
競合が発生したら、まず競合箇所をエディタで修正し、修正後に以下のコマンドを実行してください。
git add 修正したファイル git rebase --continue
これを繰り返すことで、競合解決後も順調にrebaseを進められます。
もし操作に失敗してしまったり、履歴が思わぬ形で壊れてしまったりした場合、git reflog を使えば直前の状態に戻せる可能性があります。
reflogでは、これまでのコミット操作の履歴を確認できるため、やり直しが効くのです。
git squash がもたらすメリット
ここで改めて、git squash によるメリットをまとめてみましょう。
- 履歴がスリムになり把握しやすい
- コミットメッセージを一括で修正できる
- レビューの際に差分を確認しやすくなる
実務においては、短期的には細かいコミットを繰り返し、最終的にマージ前にきれいにまとめることが多いです。
この作業フローを身につけると、チームでの開発効率が上がり、履歴を読み返すときに「何をいつやったのか」が理解しやすくなります。
まとめ
ここまで、git squash の基本的な使い方と実務での活用シーンを解説しました。
複数のコミットを1つにまとめることで、履歴をスッキリ保ち、レビューの手間を減らすことができます。
ただし、共同作業中のブランチに対しての実行や、force push には注意が必要です。
コミットをまとめるタイミングや粒度を上手に見極めれば、チーム開発におけるコミュニケーションや管理が大幅に楽になります。
細かくコミットを残しておきながら最終的に綺麗な履歴を作ることは、Gitの便利な使い方のひとつです。
ぜひ、今後のプロジェクトで試してみてはいかがでしょうか。