git 子模块究竟是如何工作的

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/12078365/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-19 07:23:55  来源:igfitidea点击:

how exactly does git submodule work

gitgit-submodules

提问by dacongy

The .gitmodulefile only specifies the module repository url. How does git submoduleknow which version to download? It seems to be always checking out the latest version. Then, how does developers ensure compatibility between the main project and the sub modules?

.gitmodule文件仅指定模块存储库 url。如何git submodule知道下载哪个版本?它似乎总是在检查最新版本。那么,开发者如何保证主项目与子模块的兼容性呢?

回答by VonC

Your submodule is represented as a special entry with a special mode (called a gitlink, see "Nested git repositories without submodules?"):
(See "Checkout past git submodule commit")

您的子模块表示为具有特殊模式的特殊条目(称为gitlink,请参阅“没有子模块的嵌套 git 存储库?”):(
请参阅“ Checkout git submodule commit”)

new file mode 160000
index 0000000..4c4c5a2

So it isn't checking out the "LATEST" version, but always a specific SHA1, and it does so in a DETACHED HEADmode(see "How to make submodule with detached HEADto be attached to actual HEAD?".

因此,它不会检查“最新”版本,而是始终检查特定的 SHA1,并且它以DETACHEDHEAD模式进行检查(请参阅“如何使子模块与HEAD实际连接分离HEAD”。

That doesn't mean you can't update a submodule, as I explain in "true nature of submodules".

这并不意味着您不能更新子模块,正如我在“子模块的真实性质”中所解释的那样。

For more on submodules, and on potentially why you might notwant to use them(!), read the sobering article "Why your company shouldn't use Git submodules", from Amber Yust(also on SO).

欲了解更多关于子模块,以及潜在为什么你可能希望使用他们(!),请阅读文章发人深省“为什么你的公司不应该使用Git的子模块”,从琥珀Yust(也对SO)。

Just one small extract, for kicks and giggles (emphasis mine):

只是一小段摘录,用于踢腿和咯咯笑(强调我的):

When you invoke git submodule updateit looks in the parent repository for a SHA for each submodule, goes into those submodules, and checks out the corresponding SHAs.
As would be the case if you checked out a SHA in a regular repository, this puts the submodule into a detached HEAD state.

If you then make changes in the submodule and commit then, Git will happily create the commit… and leave you still with a detached HEAD. See where this is going yet?

Say you merge in some more changes which happen to include another submodule update. If you haven't committed your own submodule change into the parent project yet, Git won't consider your new commit in the submodule as a conflict, and if you run git submodule updateit will happily wipe out your commit without warning, replacing it with that from the branch you just merged in.

I hope you had your submodule's reflogenabled or still have the old commit in your terminal scrollback, because otherwise, you just lost all that work you did.

当您调用git submodule update它时,它会在父存储库中查找每个子模块的 SHA,进入这些子模块,并检出相应的 SHA。
如果您在常规存储库中检出 SHA,就会出现这种情况,这会将子模块置于分离的 HEAD 状态。

如果您随后在子模块中进行更改并提交,Git 将很高兴地创建提交……并让您仍然拥有一个分离的 HEAD。看看这是怎么回事?

假设您合并了更多更改,这些更改恰好包含另一个子模块更新。如果您还没有将自己的子模块更改提交到父项目中,Git 不会将您在子模块中的新提交视为冲突,如果您运行git submodule update它,它会很高兴地在没有警告的情况下清除您的提交,将其替换为来自你刚刚合并的分支

我希望你reflog启用了你的子模块,或者在你的终端回滚中仍然有旧的提交,否则,你就会失去你所做的所有工作

Err... "ouch".

呃……“哎哟”。



Note that now a submodule can track the latest from a branch: see "git submodule tracking latest".

请注意,现在子模块可以跟踪分支的最新信息:请参阅“ git submodule tracking latest”。