
🐙 Git error 'fatal: refusing to merge unrelated histories': causes and solution
You ran git pull, and instead of the expected changes, the terminal greeted you with a red line: fatal: refusing to merge unrelated histories. The project didn't update, commits didn't pull, and you're sitting there wondering if you broke the repository.
No, you didn't break it. Git simply refuses to mix two independent histories, and this is intentional behavior, not a bug. In five minutes you'll not only understand why this error occurs, but also learn to fix it in any situation: on first push, after losing .git, and when merging disparate projects.
💡 Quick overview:
- When Git refuses to merge unrelated branches and why this is correct
- The
--allow-unrelated-historiesflag, a universal solution forpull,merge, and first push - Step-by-step scenarios: cloning without history, new repository, rebase and force-push
- What to do if the flag doesn't help, and how to avoid this error in the future
What the error means and why Git throws it
Git tracks history through a chain of commits. Each commit references its parent, building a graph that Git uses to understand what came from where. When you do git merge, Git looks for a common ancestor between two branches and calculates the difference from it.
But sometimes there simply is no common ancestor. Two commit graphs don't intersect, like two separate projects that never knew about each other. In such a situation, Git refuses to merge histories blindly and throws:
1 fatal: refusing to merge unrelated histories
This isn't an error in the usual sense. It's protection: Git is telling you, "I don't understand how these two histories are related, so I won't guess." The solution exists, and it's built into Git starting with version 2.9.0 (released in June 2016).
Two typical scenarios that lead to the error
First scenario, **corruption or deletion of the **.git directory. You cloned a project, worked with the code, but the .git folder got deleted (accidentally, by antivirus, or when copying without hidden files). Git loses all local history and when attempting git push or git pull treats your working directory as a completely new project, unrelated to the remote repository.
Second scenario, a new repository meets an existing one. You did git init, added several commits locally, then tried to connect a remote repository that already has its own history. Git sees two independent commit graphs and refuses to mix them. This often happens when you start a project from scratch, then decide to upload it to GitHub on top of an existing repository, or when transferring code from one project to another.
Both scenarios are solved by the same mechanism, but before applying it, you should understand what exactly you want to achieve: merging two histories into one or completely replacing one history with another.
Solution: the --allow-unrelated-histories flag
The key to fixing this is the --allow-unrelated-histories flag. It explicitly tells Git: "I know these branches have no common ancestor, and I consciously want to merge them." The flag works with both main commands, git pull and git merge.
**For **git pull (the most common case):
1 git pull origin main --allow-unrelated-histories
Replace main with your branch name if it differs (master, develop, etc.). Git will create a merge commit that connects the two independent histories. An editor will likely open for the commit message, describe why you're merging the histories, save and close the editor.
**For **git merge (when branches are local):
1 git merge feature-branch --allow-unrelated-histories
After successful merge, Git will prompt you to push the result. Don't forget to do this:
1 git push origin main
Important nuance: --allow-unrelated-histories doesn't remove merge conflicts. If both branches have files with the same names, Git will still ask you to resolve conflicts manually, the flag only handles connecting histories, not file contents.
Step-by-step scenarios for different situations
Situation 1: first push to a non-empty remote repository
You created a project locally (git init → commits), and on GitHub there's already a repository with README.md and .gitignore. Direct git push won't work because the remote branch contains commits you don't have.
Correct sequence:
First pull the remote history and merge it with your local:
1 git pull origin main --allow-unrelated-histories
Resolve conflicts if any exist (usually README.md conflicts), make a merge commit, then:
1 git push origin main
Situation 2: recovery after losing.git
The .git folder is deleted, but the working directory is intact. You can restore the connection to the remote repository without losing uncommitted changes:
1 git init 2 git remote add origin <repository-url> 3 git fetch origin 4 git reset --mixed origin/main
The git reset --mixed command synchronizes the Git index with the remote branch, but keeps all your working files untouched. After this, add changes and make a new commit:
1 git add . 2 git commit -m "Recovery after losing .git" 3 git push origin main
This approach is preferable to --allow-unrelated-histories because it doesn't create an artificial merge commit and keeps history clean.
Situation 3: rebase with unrelated histories
The git rebase command can also throw this error, especially when using the --preserve-merges flag (now replaced with --rebase-merges). Solution, add --allow-unrelated-histories:
1 git rebase --rebase-merges --allow-unrelated-histories main
But be careful: rebase rewrites history, and if someone else is working with this branch, you'll create problems for them. For shared branches, always prefer merge.
What to do if the flag doesn't help
Sometimes --allow-unrelated-histories works without errors, but the result isn't what you wanted.
Problem: merge commit clutters history. If you merged two large projects, the commit graph becomes hard to read. In this case, consider an alternative, transferring files with history preservation via git format-patch and git am:
1 git format-patch --root -o patches/ HEAD 2 git am patches/*.patch
Problem: after merge the project doesn't compile. Merging unrelated histories can lead to duplicate configuration files, dependency conflicts, or incompatible package versions. After --allow-unrelated-histories always check: dependencies (npm install / composer install), configuration files (.env, config/), paths and imports in code. Better to spend five minutes on verification now than deal with failing builds in CI later.
Problem: you changed your mind. You can roll back a merge of unrelated histories the standard way, git reset --hard HEAD~1 (if you haven't pushed the result yet) or git revert -m 1 HEAD (if you already pushed).
How to avoid the error in the future
Three simple rules that will spare you this error in daily work.
Don't delete .git without absolute necessity. If you need to copy code without history, use git archive or copy files excluding the hidden .git folder consciously, not accidentally.
Don't create a new repository inside an existing one. If you need to extract part of the codebase into a separate project, use git subtree split or git filter-branch (now git filter-repo is recommended). These tools will preserve the history of needed files, and Git will know where they came from.
Before git init in a folder with code, always check if there's already a repository there: git status. If Git responds fatal: not a git repository, you can initialize. If it shows status, you're already inside an existing repository and git init isn't needed here.
For those just starting to work with Git, we recommend our guide "Git guide for beginners", it walks through SSH keys, repository creation, and the complete GitHub workflow step by step. And if Git isn't installed yet, start with the guide "How to install Git on Windows".
⁉️🤔 Frequently asked questions
Which Git versions support --allow-unrelated-histories?
The flag appeared in Git 2.9.0 (June 2016) and is present in all subsequent versions. If your Git version is older, update it: the
git --versioncommand will show the current version, andgit update-git-for-windows(on Windows) or your system's package manager will update to the current release. The easiest way to check the Git version is thegit --versioncommand in the terminal. As of mid-2026, the current branch is 2.48+. If you're on Windows and Git was installed a long time ago, download a fresh installer from git-scm.com, auto-update in old versions worked unstably.
Can I use the flag with git push directly?
No,
git pushdoesn't accept--allow-unrelated-histories. Push doesn't create a merge, it only sends existing commits. The "unrelated histories" error on push means your local branch and remote have diverged at the history level. Solution: firstgit pull --allow-unrelated-histories, resolve conflicts, and only thengit push. Formally--allow-unrelated-historiesworks withgit fetch+git mergeand withgit pull(which internally does fetch + merge). Push remains a separate operation that you perform after successful merge. Don't try to bypass this with--force, you'll lose other people's commits on the remote repository.
What's better for clean history: merge or rebase?
For connecting unrelated histories, definitely
merge. Rebase in this context creates more problems than it solves: it tries to replay commits from one branch on top of another, but without a common ancestor this leads to conflicts on every commit. Merge with--allow-unrelated-historiesdoes exactly what's needed, creates one connection point between two graphs, after which history is unified. Exception: when you intentionally want to rewrite history and know exactly what you're doing. For example, when transferring code from one repository to another with cleanup from old commits. In this casegit rebase --allow-unrelated-historiescan be meaningful, but for daily work choose merge.
I lost the .git folder, but I have uncommitted changes. Will I lose them?
No, you won't lose them. The
.gitfolder itself contains only history and Git metadata, but not your working files. All modified, new, and even uncommitted files will remain in the working directory untouched. The recovery procedure is described in "Situation 2" above,git init→git remote add→git fetch→git reset --mixed. Key point: use exactly--mixed, not--hard. The--mixedflag resets the index but preserves all changes in files. If you're unsure, make a backup copy of the entire project folder before recovery, this will take ten seconds and completely eliminate the risk of data loss in any non-standard situation.
The error occurs when cloning through an IDE. Is this the same problem?
Yes, the same one. Some IDEs (for example, PHPStorm, Visual Studio, older versions of IntelliJ) when creating a project from a template initialize a new Git repository, then try to connect a remote. This is exactly the second scenario from the beginning of the article. Solution is the same: open a terminal in the project folder and execute
git pull origin main --allow-unrelated-histories. After manual merge, the IDE will pick up the new state automatically, just refresh the project window or click Refresh in the Git panel.
Should you fear the "unrelated histories" error?
No. This is one of the safest Git errors, it doesn't corrupt data, doesn't delete files, and doesn't prevent continuing work. The --allow-unrelated-histories flag isn't a crutch or workaround, but a documented capability specifically added by Git developers for cases when you consciously want to connect two independent histories.
Having mastered this command, you gain a powerful tool: now you can merge projects of any degree of isolation, transfer code between repositories, and restore work after losing .git, and all this without panic and recreating the repository from scratch. If Git taught you anything today, it's that "fatal" in its messages doesn't mean "fatal for the project", it means "I won't guess, tell me explicitly what to do."



