Merging after directory got turned into submodule

我的未来我决定 提交于 2019-12-03 15:57:48

问题


I find that working with git submodules, I often encounter problems merging between commits which do contain a given submodules and those which represent the same code as a normal directory. Small reproducing example:

# Create one project, to be used as a subproject later on
git init a
cd a
echo aaa > aa
git add -A
git commit -m a1
cd ..

# Create a second project, containing a as a normal directory initially
git init b
cd b
mkdir a b
echo aaa > a/aa
echo bbb > b/bb
git add -A
git commit -m b1

# Replace directory with submodule
git rm -r a
git submodule add ../a a
git commit -m b2

# Try to create branch from the pre-submodule state of affairs
git checkout -b branch HEAD^

This already gives an error:

error: The following untracked working tree files would be overwritten by checkout:
    a/aa
Please move or remove them before you can switch branches.
Aborting

In order to avoid the error, I deinitialize all submodules first:

# Create feature brach starting at version without submodule
git submodule deinit .
git checkout -b branch HEAD^
echo abc > b/bb
git commit -a -m b3

As you can see, the feature branch is completely unrelated to the submodule, modifying a different set of files. Which makes this whole problem particularly annoying.

# Try to merge the feature branch
git checkout master
git merge branch

This fails again, with an error message I don't fully understand:

CONFLICT (file/directory): There is a directory with name a in branch. Adding a as a~HEAD
Automatic merge failed; fix conflicts and then commit the result.

I get the same error if I do a git submodule update --init before the git merge branch. I don't see any a~HEAD anywhere, neither in my directory tree nor in the output from git status, which reads like this:

On branch master
You have unmerged paths.
  (fix conflicts and run "git commit")

Changes to be committed:

    modified:   b/bb

Unmerged paths:
  (use "git add <file>..." to mark resolution)

    added by us:     a

If I do git add a as suggested, I get another error:

error: unable to index file a
fatal: updating files failed

If I do git submodules update --init just before the merge, then I can do git add a successfully. But if I forget to do so, and then try doing that after the merge, I receive this error message:

Submodule 'a' (…/a) registered for path 'a'
Skipping unmerged submodule a

How do I recover from this situation? Something other than git merge --abort, since I'd like to use it for things like git rebase as well, and since in some scenarios (don't know how to reproduce) I couldn't even abort the merge cleanly, and had to do a hard reset instead.

How can I avoid it in the first place? Is there some magic setting which makes git do the right thing with submodules vs. directories during merges, so that I don't have to manually post-process a merge which only modifies files unrelated to the submodules?


回答1:


No you should not add a, the merge is not supposed to change it. What you should run is

git reset a

So you ignore the "chage" for a.

PS: apparently git merely checks existense of a directory, so if you

git submodule deinit a
rmdir a

before merging, it will succeed. Not sure if this is what you want.




回答2:


I got similar problem when I merge code that contains folder that need to convert to submodule.

I solved it by using BFG --delete-folders to remove the folder from the new source code, and git gc to clean up the repository, then I will have git rebase without any conflicts.



来源:https://stackoverflow.com/questions/31821219/merging-after-directory-got-turned-into-submodule

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!