メインコンテンツへスキップ
ブログ一覧に戻る
Web制作・運用

Gitのマージとは?初心者がつまずく原因と"コンフリクト回避"の考え方

2026年1月7日
最終更新: 2026年10月8日
7分で読めます

この記事でわかること

Gitのマージを、現在のブランチへの統合として説明します。fast-forwardと分岐した履歴の違いを図解し、取り込み先の確認、明示的な統合方針、競合の解決と中止を順に整理。rebaseやPRの役割、マージできない時の見方、小チームの運用を学び、統合成功を動作確認や公開成功と混同しないための判断を示します。

2026年10月8日にGitのmerge、pull、rebase公式マニュアルを再確認した。mergeは履歴を結合し、pullは取得後の統合を行い、rebaseはcommitの土台を付け替える。競合解決、共有済み履歴、レビュー、CI、ブランチ保護を別に確認し、rebaseやmergeの成功をそのまま業務承認・公開・会計・復旧の完了としない。

マージは、別の履歴で行った変更を現在のブランチへ統合する操作です。「道を合流させる」という比喩に、統合先はどこか、履歴が分岐しているか、内容をどう確かめるかの3点を加えると、操作を判断しやすくなります。

30秒で要点

  • 統合先は現在のブランチです。mainへ自動的に切り替わる操作ではありません。
  • fast-forwardは祖先関係を利用した参照の前進。競合せず処理できるマージ全般の別名ではありません。
  • 競合したら処理中の状態と変更意図を確認します。merge成功、動作確認、公開成功は別々に判断します。

2種類の履歴を図で区別する

mainがA、featureがその先のBを指すなら、mainをBへ進めるだけで取り込めます。これがfast-forwardです。新しいmerge commitは作りません。main側もAからCへ進んでいれば履歴は分岐しています。通常の2ブランチのmergeでは、BとCを親に持つMを作って合流を記録できます。git-mergeの説明に基づく区別です。

上段はAからBへmainの参照を進めるfast-forward、下段はAから分かれたBとCを親に新しいMを作るマージで、競合の有無とは別の区別である図。
FFは新merge commitを作らず、分岐の統合例では2つの親を持つMを1つ追加します。

上段はAとBの2コミットで、新しいmerge commitは0個です。下段はA・B・CにMを1つ加えた4コミットになり、Mの親は2つです。下段でも、別の場所を変更していれば競合せず統合できる場合があります。反対に、同じ人が別branchで矛盾する変更をしても競合は起こります。

ボタン機能をmainへ取り込む

最初のcommitがある練習用リポジトリで、feature/new-buttonの差分を確認済みとします。未コミット変更を保全し、統合先を確認します。

git status --short
git checkout main
git branch --show-current
git merge --ff-only feature/new-button
git log --oneline --graph --all

--ff-onlyは、分岐していて参照の前進だけでは取り込めない場合に拒否します。旧手順のgit merge feature/new-buttonや一般形git merge ブランチ名は統合の基本形ですが、許可する履歴の形を明示したい場合はこの指定が役立ちます。拒否は履歴の確認が必要という知らせであり、データが壊れた証拠ではありません。

共有remoteのmainを先に確認する元のgit pull origin mainには、取得と統合の両方が含まれます。何も考えずgit pullを追加するのではなく、取得元、現在branch、チームの統合方針を確認します。詳しい区別はプルの説明を参照してください。

分岐した履歴と競合を扱う

分岐を残して統合する方針で、両branchの内容と作業ツリーを確認した練習では、次のようにmerge commitを作れます。

git merge --no-ff feature/new-button -m "ボタン機能を統合"
git log -1 --format=%P
git status --short

2つのbranchのmerge commitなら、親commitの識別子が2つ表示されます。親の数が2つでも、取り込んだ機能が正しい保証にはなりません。たとえば価格表示と割引条件を別々に変えたとき、テキスト上は競合しなくても組合せが誤ることがあります。

競合時は、まずstatusで処理中の状態と対象ファイルを確認します。ファイル中の区切り記号を消すだけでは解決になりません。共通の起点と両側の意図を読み、最終的に必要な内容を作ります。

git status
git diff --name-only --diff-filter=U
git add button.txt
git merge --continue

この最後の2行は、button.txtの競合を編集して解決し、対象がそれだけであると確認した後に実行します。必要に応じてメッセージのエディタが開きます。他にも未解決ファイルがあれば、それぞれ解決します。取り込みをやめる場合のgit merge --abortは、開始前の状態の再構成を試みますが、開始前からあった未コミット変更を常に完全復元できる約束ではありません。そのため開始前の保全が重要です。

どの作業をまとめるのか

表が収まらない場合は、横にスクロールできます

元の教材の作業例branch名の例統合前に見る点
ブログへのコメントfeature/comment-system投稿・表示と既存記事への影響
デザイン更新design/new-layout読みやすさと既存操作の維持
支払い機能feature/apple-pay、feature/payment成功だけでなく失敗や取消の扱い
ログイン修正fix/login-error元の不具合が再現しなくなるか
追加機能の並行作業feature/user-profile、feature/search、feature/notification各変更と組合せの動作

これらは命名と確認観点の架空例です。Gitへの統合だけで決済サービスや通知が利用可能になるわけではありません。branch名も、merge後に自動削除されるものではありません。

rebaseとPRを使うときの役割

rebaseは別の起点へcommitを再適用する方法で、元と異なるcommitになる場合があります。git-rebaseの図ではA・B・CがA′・B′・C′として表現されています。分岐の合流を残すmergeと、履歴をつなぎ直すrebaseは、見た目だけで選ばず共有状態とチーム方針で決めます。共有済み履歴を他者の合意なく書き換えません。

PRは、差分・目的・確認結果を人が読む入口です。レビュー待ちに別の変更が入った場合は、現在の組合せでも問題ないか確認します。PRを作っただけで事故が防げるわけではありません。

「マージできない」時のチェック項目

表が収まらない場合は、横にスクロールできます

確認する順序見るもの次の判断
現在地branch名と統合対象意図した宛先か確認する
作業途中未コミット差分、処理中のmerge/rebase保全して完了または中止する
履歴FF可能か、別の根から始まっていないかチームで許した統合方式を選ぶ
競合内容変更理由と最終的な振る舞い解決・stage・続行後にテストする

小チームでは、短い目的単位、取り込む前の確認、統合後の検証から始められます。エラーを消すために無関係な履歴の統合や強制操作を追加する必要はありません。

関連する学習経路

よくある質問(FAQ)