LoginSignup
4
1

More than 1 year has passed since last update.

【Git】pushもできない初心者が、エラー「fatal: refusing to merge unrelated histories」を乗り越えた話。

Last updated at Posted at 2022-08-08

概要

・ 初心者がgitコマンドで遊んでいたら、いつの間にかpushできなくなっていた。
pushできない原因をfatal: refusing to merge unrelated historiesに特定。
・ 最終的に自分が何をやらかしたのか推測(なんのコマンドを実行したか覚えていないため)。

fatal: refusing to merge unrelated historiesに対する結論は、「解決法」に記載がございます。

環境

terminal
% git --version
git version 2.36.1

※リモート名「origin」、ブランチ名「main」で作業しています。

エラー状況

①. 「main」ブランチをpushしようとしたところ、エラーが発生
②.  エラー文に基づいて、「main」ブランチをpullを実行するも再度エラーが発生
③.  再度出たエラー文に基づいて、config pull.rebase falseを実行し、再度pullするも再再度エラーが発生


それぞれ状況を確認していきます。

エラー状況①

「main」ブランチをpushしようとしたところ、下記のエラーが発生した。

terminal
% git push origin main
To https://github.com/xxxxxxxxxxxxxxxxxxx
 ! [rejected]        main -> main (non-fast-forward)
error: failed to push some refs to 'https://github.com/xxxxxxxxxxxxxxxxxxx'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. Integrate the remote changes (e.g.
hint: 'git pull ...') before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.
  • エラー文の内容は以下の通り。
    • xxxxxxxxxxxxxxxxxxxにpushできなかったよ
    • リモートブランチより現在のブランチが古いから、拒否されたよ
    • pushする前に、リモートの変更を統合してね(例えばgit pullでね)

エラー文中の(non-fast-forward)について、GitHub Docsによると、

別の人が同じブランチにすでにプッシュしてしまった場合、Git はあなたの変更をプッシュできません。

別の人はいない(自分一人でしか作業をしていない)ので、自分が既にリモートリポジトリへpush済みであることが原因のよう。

とりあえずエラー文の指示通り、pullを実行してみることに...

エラー状況②

pullを実行したところ、またエラーが発生。下記の通り。

terminal
% git pull origin main
From https://github.com/xxxxxxxxxxxxxxxxxxx
 * branch            main       -> FETCH_HEAD
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.
  • エラー文の内容は以下の通り。
    • 分岐したブランチがあって、それらを一致させる方法を指定する必要があるよ
    • 次のpullの前に、次のコマンドのうちのどれかを実行すればそれができるよ
      (git config以下略)

エラー文の指示通り、1つめのコマンドgit config pull.rebase falseを実行し、
その後に再度pullをしてみることに...

エラー状況③

pullを実行したところ、下記のエラーが発生。またpull出来ず...

terminal
% git pull origin main
From https://github.com/xxxxxxxxxxxxxxxxxxx
 * branch            main       -> FETCH_HEAD
fatal: refusing to merge unrelated histories
  • エラー文の内容は以下の通り。
    • 関係ない履歴同士はmergeできないよ

どうやら問題の根本はunrelated historiesmergeできないことにありそうです。

解決法

下記のコードを実行することで、強制的にリモートリポジトリの内容をローカルに引っ張ってくることができ、最終的にpushすることができました。

terminal
% git merge --allow-unrelated-histories origin/main

公式Docによる--allow-unrelated-historiesオプションの詳細は以下の通りです。

--allow-unrelated-histories
By default, git merge command refuses to merge histories that do not share a common ancestor.
This option can be used to override this safety when merging histories of two projects that started their lives independently.
As that is a very rare occasion, no configuration variable to enable this by default exists and will not be added.

  • --allow-unrelated-histories
    • "merge"コマンドは、共通の祖先を持っていない履歴同士を"merge"できないよ
    • 独立して生成された2つのプロジェクトの履歴を"merge"したい時は、このオプションを使えばOK!
      (As that以下略)

なるほど、共通の祖先を持っていないもの同士をmergeしようとしていたことが、本問題の原因であると特定できました。

自分がやらかしたことを推測

自分が行った行為は下記の通りと推測されます。

①.  git.initで「ローカルリポジトリA」を作成
②.  Aで管理されたデータをリモートリポジトリにpush
③.  git.initで別の「ローカルリポジトリB」を作成
④.  Bで新規作成したデータを、②でpushしたのと同じリモートリポジトリ・ブランチにpush←ここで最初のエラー発生
⑤.  共通の祖先を持っていないためpullできない←次のエラー発生

たぶんこんな感じなのかな??

最後に公式Docに出てきた「共通の祖先を持っている」とは、共通の親コミットを持っているということなのでしょうか。
上記の③でローカルBを作成後、開幕一発目のコミットデータには当然親コミットは存在しないので、共通の親を持っているどころではありませんね。

大変勉強になりました。

参考にした記事

4
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
1