我有一个Mercurial存储库,并且毫无问题地添加了git subrepo(hg 1.8)。
问题是:这个git subrepo内部有另一个git子存储库,并且没有被 pull 出(它在git的subrepo .gitmodules
文件中),除非我在git subrepo上执行了git clone --recursive
:这样可以正常工作。
问题:我在另一台计算机的存储库中执行了hg pull
,它 pull 出git subrepo
,但没有 pull 出.gitmodules
。 .gitmodules仅在我执行git clone --recursive
时才 pull 入另一台计算机中。
有人对这种情况有什么建议吗?丑陋的解决方案是执行git clone
并简单地将所有文件(包括git元数据)添加到我的Merurial存储库中,而不像子仓库一样。
最佳答案
我认为最好的解决办法是修补Mercurial的Git子存储库支持,以始终使用Git的递归选项(例如,克隆基于Git的子存储库时为git clone --recursive
,在提取更新的基于Git的子存储库后为git pull --recurse-submodules && git submodule update
等)。我知道Git开发人员特别选择不自动初始化子模块,因为他们要支持的工作流程之一是“我从不希望看到任何子模块”,但也许“总是初始化所有子存储库”是与之更好的匹配。默认的Mercurial操作模式(我不是Mercurial的用户,所以我对默认的Mercurial样式不会有什么好主意)。
在此之前,您也许可以通过将subrepo/.gitmodules
条目转换为.hgsub
条目来解决此问题。手动操作很容易,但是如果很重要,则可以将其自动化(使用git config
从.git/config
和/或.gitmodules
提取路径和URL)。如果您正在处理一个变化很大的.gitmodules
文件,这可能没有吸引力(每次.hgsub
更改时,您必须非常勤奋地同步.gitmodules
)。
我用四个存储库对此进行了测试:
gitsub/
是gitsub作为子模块gitsuper/
是gitsuper作为子存储库,gitsuper/gitsub
是gitsub作为子存储库。 gitsuper/
是gitsuper作为子存储库,gitsuper/gitsub
是gitsub作为子存储库。 我像这样构建并测试了它们:
git submodule add url-of-gitsub gitsub && git submodule init
git commit -m 'added gitsub'
git clone --recursive url-of-gitsuper gitsuper
echo 'gitsuper = [git]url-of-gitsuper' >> .hgsub
echo 'gitsuper/gitsub = [git]url-of-gitsub' >> .hgsub
这最后两个步骤可以从gitsuper/.git/config
和gitsuper/.gitmodules
的位自动执行。 hg add .hgsub && hg commit -m 'added Git subrepositories'
它在
gitsuper/
和gitsuper/gitsub/
中获取适当的内容。 (cd gitsub && git pull origin master)
git add gitsub && git commit -m 'updated gitsuper content (also gitsub)'
(cd gitsuper && git pull --recurse-submodules && git submodule update)
下 pull 菜单中会更新gitsuper/
和gitsuper/gitsub/
中的内容。 hg commit -m 'updated gitsuper (and its contents)'
hg pull -u
来自Git的内容已更新。 我的测试有效(使用Mercurial 1.8.1和Git 1.7.4.1),但是我注意到一个错误。 Mercurial会创建并 checkout 一个奇怪的Git分支(
origin/master
(即refs/heads/origin/master
)而不是使用分离的HEAD(就像Git对其子模块所做的那样)或仅使用master
(即refs/heads/master
))。它有时似乎也会变得有些楔形,从而导致如下错误:fatal: git checkout: branch origin/master already exists
abort: git checkout error 128 in gitsuper
我通过进入有问题的Git存储库(基于Git的Mercurial子存储库)并使用
git checkout HEAD~0 && git branch -D origin/master
删除分支来解决该问题(第一个分离HEAD,(更重要的是)移出该分支,以便可以在下一个删除它命令)。只要您在Git存储库中没有任何本地更改更改,此变通办法是完全安全的。另一个小问题是,在Mercurial创建的Git super 存储库中发布Git子模块命令之前,您需要运行
git submodule init
让Git知道其子模块(这些子模块被克隆到正确的位置,但是它们是由Mercurial建立的,因此.git/config
中没有任何条目。同样,如果您计划从基于Git的Mercurial子存储库内部创作对Git管理的内容的更改,那么在提交Mercurial之前,请务必始终添加所有Git子模块,进行提交并从Git子存储库中推送, “ super 项目”。否则,您可能会遇到这样的情况:Mercurial使用gitsuper和gitsub的一种组合,而gitsuper本身指的是gitsub的不同版本。换句话说,由于您将绕过Git的子模块代码(通过将Git子模块作为Mercurial子存储库进行管理),因此您需要注意保持Git对子模块的看法与Mercurial的观点保持同步。
关于git - 使用在Mercurial存储库中具有另一个git subrepo的git subrepo,这可能吗?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/5420664/