86

背景

在 Linux 上使用 Git 1.8.1.1。存储库如下所示:

master
  book

子模块创建如下:

$ cd /path/to/master
$ git submodule add https://user@bitbucket.org/user/repo.git book

book子模块是干净的:

$ cd /path/to/master/book/
$ git status
# On branch master
nothing to commit, working directory clean

问题

另一方面,master 显示 book 子模块有“新提交”:

$ cd /path/to/master/
$ git status
# On branch master
# Changes not staged for commit:
#   (use "git add <file>..." to update what will be committed)
#   (use "git checkout -- <file>..." to discard changes in working directory)
#
#       modified:   book (new commits)
#
no changes added to commit (use "git add" and/or "git commit -a")

Git 应该完全忽略子模块目录,这样 master 也是干净的:

$ cd /path/to/master/
$ git status
# On branch master
nothing to commit, working directory clean

失败的尝试 #1 - 脏

根据此答案,文件内部master/.gitmodules如下:

[submodule "book"]
        path = book
        url = https://user@bitbucket.org/user/repo.git
        ignore = dirty

失败的尝试 #2 - 未跟踪

根据此答案更改master/.gitmodules为以下内容:

[submodule "book"]
        path = book
        url = https://user@bitbucket.org/user/repo.git
        ignore = untracked

尝试失败 #3 - showUntrackedFiles

根据this answer编辑master/.git/config为以下内容:

[status]
   showUntrackedFiles = no

失败的尝试 #4 - 忽略

将 book 目录添加到主忽略文件中:

$ cd /path/to/master/
$ echo book > .gitignore

失败的尝试 #5 - 克隆

将 book 目录添加到 master 中,如下所示:

$ cd /path/to/master/
$ rm -rf book
$ git clone https://user@bitbucket.org/user/repo.git book

问题

子模块如何book位于存储库下自己的存储库目录中,master而 git 忽略book子模块?也就是说,不应显示以下内容:

#
#       modified:   book (new commits)
#

git status在主存储库中执行时如何抑制该消息?

一篇关于git submodule pitfalls的文章表明这​​是不适当的子模块使用?

4

6 回答 6

109

赶紧跑:

$ git submodule update

这会将子模块恢复为旧提交(在 parent-repo 中指定),而不使用子模块的最新版本更新 parent-repo。

于 2013-09-17T15:55:48.930 回答
61

要包含另一个不需要在其超级存储库中跟踪的存储库,请尝试以下操作:

$ cd /path/to/master/
$ rm -rf book
$ git clone https://user@bitbucket.org/user/repo.git book
$ git add book
$ echo "book" >> .gitignore

然后提交。

如链接的git 子模块陷阱文章中所述:

...父模块和子模块之间的唯一联系是存储在父模块提交中的子模块签出 SHA 的记录值。

这意味着子模块不是由其签出的分支或标签保存的,而是始终由特定的提交保存的;该提交(SHA)像普通文本文件一样保存到超级存储库(包含子模块的存储库)中(当然,它被标记为此类引用)。

当您在子模块中签出不同的提交或在其中进行新提交时,超级存储库将看到其签出的 SHA 已更改。那是你modified (new commits)git status.

要消除这种情况,您可以:

  • git submodule update,这会将子模块重置为当前保存在超级存储库中的提交(有关详细信息,请参见手册git submodule;或
  • git add book && git commit将新的 SHA 保存到超级存储库中。

正如评论中提到的,考虑放弃book子模块:如果不需要将其状态作为超级回购的一部分进行跟踪,则将其克隆到超级回购中。

于 2013-01-20T07:17:12.253 回答
21

您可以抑制两种更改通知(来自 git 1.7.2)。

第一个是未跟踪的内容,当您对子模块进行更改但尚未提交这些内容时会发生这种情况。父存储库注意到这些并且 git status 相应地报告它:

modified: book (untracked content)

您可以使用以下命令抑制这些:

[submodule "book"]
    path = modules/media
    url = https://user@bitbucket.org/user/repo.git
    ignore = dirty

但是,一旦您提交了这些更改,父存储库将再次注意到并相应地报告它们:

modified:   book (new commits)

如果您也想抑制这些,则需要忽略所有更改

[submodule "book"]
    path = book
    url = https://user@bitbucket.org/user/repo.git
    ignore = all
于 2014-10-21T09:47:23.197 回答
10

Git 2.13(2017 年第二季度)将添加另一种方式来包含不需要由其父 repo 跟踪的子模块。

在OP的情况下:

git config submodule.<name>.active false

请参阅提交 1b614c0提交 1f8d711提交 bb62e0a提交 3e7eaed提交 a086f92(2017 年 3 月 17 日)和提交 ee92ab9提交 25b31f1提交 e7849a9提交 6dc9f01提交 5c2bd8b(2017 年 3 月 16 日),作者为Brandon Williams mbrandonw
(由Junio C Hamano 合并 -- gitster--提交 a93dcb0中,2017 年 3 月 30 日)

submodule: 解耦 url 和子模块的兴趣

当前,submodule.<name>.urlconfig 选项用于确定给定的子模块是否对用户感兴趣。在我们希望在不同的工作树中检查不同的子模块或更通用的机制来选择感兴趣的子模块的世界中,这最终会变得很麻烦。

在未来工作树支持子模块时,将会有多个工作树,每个工作树可能只需要检出子模块的一个子集。
URL(这是可以获取子模块存储库的位置)在不同的工作树之间不应有所不同。

用户更容易指定他们感兴趣的子模块组,而不是git submodule init <path>在他们希望在工作树中检出的每个子模块上运行“”,这也可能很方便。

为此,引入了两个配置选项,submodule.active并且 submodule.<name>.active.

  • 配置包含一个路径规范,submodule.active它指定工作树中应该存在哪些子模块。
    • submodule.<name>.activeconfig 是一个布尔标志,用于指示该特定子模块是否应该存在于工作树中。

重要的是要注意它的submodule.active功能不同于其他配置选项,因为它需要一个路径规范。
这允许用户采用至少两个新的工作流程:

  1. 子模块可以用一个前导目录分组,这样一个路径规范,例如“ lib/”将覆盖所有库模块,以允许那些对库模块感兴趣的人设置“ submodule.active = lib/”一次,说明“”中的任何和所有模块lib/都是有趣的。
  2. 一旦发明了 pathspec-attribute 特性,用户可以用属性标记子模块来对它们进行分组,这样一个具有属性要求的广泛的 pathspec,例如' :(attr:lib)',可以用来表示任何和所有具有 ' lib' 属性的模块都是有趣的。
    由于.gitattributes文件和文件一样.gitmodules是由超级项目跟踪的,所以当一个子模块在超级项目树中移动时,项目可以调整哪个路径获取属性.gitattributes,就像它可以调整哪个路径有子模块一样.gitmodules
于 2017-04-16T17:53:44.393 回答
2

Nevik Rehnel 的回答对于您所问的问题肯定是正确的:我不想拥有一个子模块,我该如何摆脱这种情况?!.

仅,如果您的master项目需要book子模块,那么保留它是一个很好的姿态,因为这样其他签出您的项目的用户就可以享受没有任何特殊git命令要运行的乐趣(嗯......有一些特殊的命令可以使用子模块,但总的来说,我认为它仍然更易于管理。)

在您的情况下,您在book存储库中进行更改,并在某些时候提交这些更改。这意味着您在该子模块中有新的提交,其中有一个新的 SHA1 引用。

您需要在主目录中做的是在主存储库中提交这些更改。

cd /path/to/master
git commit . -m "Update 'book' in master"

这会将 SHA1 引用更新为存储库master中可用的最新版本。book因此,此提交允许其他人在提示处签出所有master&book存储库。

因此,实际上,每当您对子模块进行更改时,您都会再次提交一次。如果您还对存储库中的某些文件进行更改,这是半透明的,master因为您会同时提交这两个文件。

于 2017-11-27T03:13:54.480 回答
-5

git submodule update 

在根级别。

于 2014-01-30T22:53:06.317 回答