为什么git checkout不会自动更新git子模块?


78

当使用git checkout切换分支时,我会假设大多数时候您都想更新子模块。

  • 在什么情况下,你希望更新子模块切换后?
  • 如果通过git checkout自动完成该操作会怎样?

更新了示例:

  • 分支A在3852f1具有子模块S
  • 分支B在fd72d7具有子模块S

在分支A上,git checkout B将生成分支B的工作副本,其子模块为3852f1(具有经过修改的S)。git子模块更新将在fd72d7检出S。



2
我同意你。我正在处理带有子模块的项目,每次拉动后我都应该执行git子模块更新,但是在大多数时候是不必要的。这样做的唯一理由-当子模块之一实际更新时,不要错过。
Evgen Bodunov 2011年

Answers:


26

我认为不自动更新的子模块符合Git的开发目标。Git旨在以分布式模式工作,并且除非您明确告知,否则它甚至不会假定您甚至可以连接到非本地存储库。考虑到这种方式,Git不自动刷新子模块将是预期的行为。

话虽如此,如果您知道您始终希望引入这些子模块,并且您永远不会将这些子模块分支到另一个本地存储库,那么如果您在之后自动刷新它们,则它不会破坏任何内容结帐。


49
我认为git checkout应该只是抱怨子模块的提交不可用,而不是默认使工作目录处于不一致状态。然后,您可以进行git子模块更新以获取引用的提交。同样,通常,提交将可用,并且无需任何网络访问即可完成签出。接受您的回答,因为这听起来合理(但我不喜欢它;)
serbaut

2
我的第二个想法是git应该尝试执行子模块初始化并在初始签出时进行更新,并抱怨是否存在子模块,并且该子模块尚未在本地首次拉出。有了它之后,需要显式更新的概念就很有意义了,因为存储库是不同的,并且子模块引用了特定的提交。但是,即使在可能无法使用它的分布式世界中,您也很可能会在某个时候想要它,而git应该让您知道它从未被拉过。
Cclark

6
git fetch有一个选项可以自动获取子模块,所以同样,我认为签出应该有一个类似的选项来自动更新/签出子模块。
void.pointer 2014年

3
考虑到这种方式,不自动刷新子模块将是预期的行为。” -我不明白为什么。确实,我看不出您的第一段中的任何要点与Git在拉动时是否应自动尝试更新子模块有什么关系。
Mark Amery

2
当您要在存储库上执行工作时,Git不会假定您始终有权访问从中签出的存储库。相反,一旦克隆,您的存储库就可以完全独立发挥作用。如果最初的假设是您仅在接到提示时才连接到外部存储库,那么结果就是Git不应自动刷新我试图传达的子模块。
亚伦2015年

34

git checkout --recurse-submodules 被添加到git 2.13

发行说明中提到了这一点: https //github.com/git/git/commit/e1104a5ee539408b81566066aaa6963cb87d5cd6#diff-c24776ff22455a30fbb78e378b7df0b0R139

submodule.recurse 选项已添加到git 2.14

设置:

git config --global submodule.recurse true

man git-config 说:

指定默认情况下命令是否递归到子模块中。这适用于所有具有--recurse-submodules选项的。默认为false。

我觉得默认情况下不更新模块是一个糟糕的Git默认行为,这违背了大多数用户的期望,并限制了子模块的采用,我真的希望开发人员能够对其进行更改。


2
submodule.recurse似乎从git 2.14开始工作。
凯恩'18

2
我已经submodule.recurse设定为true,但我觉得还是有次(来回跳跃跨越另外一个子模块的,我觉得呢?),我必须做git submodule update --init --recursive我的后git checkout。有没有办法使这种情况自动发生?

2

在Git 2.27(2020年第二季度)中,“ --recurse-submodules”选项的文档更好。

请参阅Damien Robert()的commit acbfae3commit 4da9e99commit d09bc51commit b3cec57commit dd0cb7d(2020年4月6日damiens-robert
(通过合并JUNIOÇ滨野- gitster-提交cc908db 4月28日2020)

doc--recurse-submodules主要适用于活动子模块

签字人:达米恩·罗伯特签字人
:菲利普·布兰

该文档指的是“已初始化”或“填充”子模块,以解释哪些子模块受“ --recurse-submodules”影响,但此处的真正术语是“ active”子模块。相应地更新文档。

一些术语:

--recurse-submodules选项主要影响活动的子模块。

一个例外是git fetch该选项影响填充的子模块。
结果,git pull --recurse-submodules访存中会影响填充的子模块,但最终的工作树更新只会影响活动的子模块。

在的文档中git-pull,让我们区分影响填充子模块的获取部分和仅影响活动子模块的工作树更新。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.