使用没有.gitmodules的Git子模块

时间:2011-08-25 20:04:00

标签: git git-submodules

我对在一个特定的情况下感兴趣,你手动将一个Git存储库放在另一个Git存储库中(通过使用git clone或通过文件系统中的copy-pasting)。我注意到当你这样做时会发生以下事情:

       
  1.       Git将保存指向特定提交的指针,就像子模块一样。    
  2.    
  3.       Git不允许你从中修改子项目的内容       超级项目,与子模块一样。    
  4.    
  5.       超级项目上的git clone不会复制子项目内容,       喜欢子模块。    
  6.    
  7.       git submodule无效。它抱怨.gitmodules不存在       那里。    
  8. 我想知道:

         
    •       .gitmodules有什么作用?缺席是a之间唯一明显的区别       像这样的手动复制和真正的子模块。    
    •    
    •       还有其他我不知道的差异吗?    
    •    
    •       此手动复制的状态是否具有特殊名称?    
    •    
    •       有没有办法覆盖和/或解决效果3和4? (IE:我想       渲染生成的存储库完全可用)    

2 个答案:

答案 0 :(得分:1)

我认为唯一的区别是子模块与其父模型有关系。例如,您可以在克隆时使用--recursive选项一次获取所有子模块。否则,您必须逐个获取它们。

答案 1 :(得分:0)

我认为(我不确定)这是子模块的实现细节。如果添加了存储库中的存储库(使用git add),则不存储目录的内容,而是存储HEAD提交的哈希值(作为类型提交而不是类型树或blob)。如果您有子存储库,此提交哈希包含您需要的所有信息。但是,如果您只有超级存储库和子存储库的HEAD的提交哈希,您仍然需要获取子存储库。此信息存储在.gitmodules文件中。如果你根本不使用遥控器,如果你从不克隆,推或拔你的超级存储库,你实际上可以使用没有.gitmodules的子模块。只需清点存储库中的子存储库(例如第三方库)。这允许跟踪超级存储库中用于每个提交的第三方库的哪个版本。但它不允许一次克隆所有内容。子存储库的远程存储器仅存储在工作树中的克隆中。如果您推送超级存储库(到裸存储库),则丢失从哪里获取子模块的信息。

要了解其工作原理cat-file是一个非常有用的工具,可以查看单个git objects。提交包含消息,作者,命名者以及通常是树对象的链接:

$ git cat-file -p 218f61f0ae29941edcc594bde692145f7f1177cc
tree 916a626892af1cd59ff84c3b7d351fca12712806
author lumbric <not-real-adress@gmail.com> 1513291656 +0100
committer lumbric <not-real-adress@gmail.com> 1513291690 +0100

Commit message in the super repository

树对象包含其他git对象的列表:

$ git cat-file -p 916a626892af1cd59ff84c3b7d351fca12712806
100644 blob e69de29bb2d1d6434b8b29ae775ad8c2e48c5391    a
100644 blob e69de29bb2d1d6434b8b29ae775ad8c2e48c5391    b
100644 blob e69de29bb2d1d6434b8b29ae775ad8c2e48c5391    c
040000 tree 765b32c65d38f04c4f287abda055818ec0f26912    folder_a
160000 commit 77e2f79e6401f28cab5cf4ca62bb0d58c945f823  sub_repo1

文件夹存储为树对象(再次包含一些git对象)和文件作为blob。子模块在树对象中存储为类型提交。内容可以在子存储库中的给定哈希中找到。

来自man git-submodule

  

子模块由一个所谓的gitlink树条目组成   引用特定提交的主存储库          内部存储库中的对象是完全独立的。 .gitmodules中的记录(参见gitmodules(5))文件          源树的根为子模块分配逻辑名称,并描述子模块应克隆的默认URL          从。逻辑名称可用于在本地存储库配置中覆盖此URL(请参阅子模块init)。