エンジニアを目指す初学者に向けて、わかりやすく解説したブログです。

リモートブランチとローカルブランチの履歴が衝突したときの解決方法

事象

git pullしたときに、以下のようなエラーが発生する。

$ git pull
remote: Enumerating objects: 68, done.
remote: Counting objects: 100% (68/68), done.
remote: Compressing objects: 100% (7/7), done.
remote: Total 56 (delta 49), reused 56 (delta 49), pack-reused 0 (from 0)
Unpacking objects: 100% (56/56), 5.70 KiB | 89.00 KiB/s, done.
From github.com:Sample/sample
 + 0a76533c...dfec07f8 feature/557 -> origin/feature/557  (forced update)
hint: You have divergent branches and need to specify how to reconcile them.
hint: You can do so by running one of the following commands sometime before
hint: your next pull:
hint:
hint:   git config pull.rebase false  # merge
hint:   git config pull.rebase true   # rebase
hint:   git config pull.ff only       # fast-forward only
hint:
hint: You can replace "git config" with "git config --global" to set a default
hint: preference for all repositories. You can also pass --rebase, --no-rebase,
hint: or --ff-only on the command line to override the configured default per
hint: invocation.
fatal: Need to specify how to reconcile divergent branches.

ローカルの履歴は全て捨てて良い場合

  • リモートブランチ:完全に正しい
  • ローカルブランチ:捨ててもいい

この場合は、ローカルブランチに対してリモートブランチで上書きすれば良い。

git fetch origin
git reset --hard origin/develop
  1. git fetch origin:リモートの最新状態をローカルに取得する(取得するだけ)
    1. origin/develop:リモートの正しい状態が反映されている
    2. ローカルのdevelop:まだ古い状態
  2. git reset —hard origin/develop
    1. ローカルブランチを origin/developと完全一致させる

リモートの内容とローカルの内容を統合したい場合

どちらの履歴も残したい場合は、merge方式とrebase方式の2通りの方法が存在する。

以下の状況を想定する。

  • リモートブランチ:Cがコミットされて進んでいる
  • ローカルブランチ:DとEの修正をローカルでしてしまっている
A---B---C   origin/develop
     \
      D---E  develop (local)

merge方式で統合する場合

イメージ

新しいマージコミット Mを作成して統合する形となる。

A---B---C------M   develop
     \        /
      D---E--

操作方法

git pull --no-rebase

もしくは

git fetch origin
git merge origin/develop

rebase方式で統合する場合

イメージ

ローカルで発生していた DEのコミット履歴をrebaseし、D’E'として新しく作成する。

A---B---C---D'---E'   develop

操作方法

git pull --rebase

もしくは

git fetch origin
git rebase origin/develop