前言
子模块这个概念在之前的 《Pro Git》笔记二:关于远程仓库的一些思考和记录中已经提到过,应该说这是一个在使用多个开源项目的项目中一定会用到的一个概念。
子模块的使用情景
在一个项目中需要使用第三方开源项目时。
子模块允许你将一个 Git 仓库当作另外一个 Git 仓库的子目录,这允许你克隆另外一个仓库到你的项目中并且保持你项目仓库的提交相对独立。该这么理解这句话呢?请看下面详细分析。
为什么需要有子模块?
假如没有子模块,那当我们需要在一个项目 A 中使用另一个项目 B 的源码时,我们只能将项目 B 的源码放到我们的项目 A 的目录中,这样会有什么影响吗?有。在这种情况下,项目 B 的源码完全没有独立的意义,项目 B 的源码对于项目 A 的项目仓库来讲,只不过是新增的一些文件而已。以后,如果我们需要对项目 B 的源码进行定制,也就是说进行修改,那对这些修改进行提交时,相应的提交对象是属于项目 A 的项目仓库的。如果项目 A 中用到的项目 B 的源码版本永远不变还好,但是假如现在项目 A 打算使用项目 B 的一个新版本的源码,那我们以前对项目 B 的源码进行的定制,怎样应用到项目 B 的新版本的源码上呢?在这种情况下应该是非常麻烦的。
但是,如果这里我们使用子模块,就不会存在这个问题了。这种情况下,虽然项目 B 的源码仍然处于项目 A 的目录下。但是,此时项目 B 的源码是完全独立于项目 A 的项目仓库的,项目 B 有自己的项目仓库。我们对项目 B 的源码进行定制时所产生的提交对象是属于项目B的项目仓库的。如果以后项目 A 想采用项目 B 的新版本的代码,我们只需要将项目 B 的项目仓库的相应分支和对应的远程分支衍和一下,然后修改下项目 A 使用的项目 B 的相应版本就可以了。
在使用子模块的情况下,上面项目 A 和项目 B 之间的关系该如何理解?
可以这样理解,首先对于项目 B 来讲,它完全不知道项目 A 的存在,也完全不需要和项目 A 有任何主动交流。对于项目 A 来讲,项目 B 可以认为是一个保存了项目 B HEAD 的文件,这个文件表示项目 A 现在使用的项目 B 的源码的版本,每当项目 B 的 HEAD 变化时,这个文件也就变化了,和其他项目 A 的普通文件一样,此时在项目 A 的目录下输入 git status 命令时,我们就可以看到它的变化。这时,我们可以选择提交,这表示项目 A 将使用项目 B 的新的一个版本。也可以选择无视,这样表示项目 A 使用的项目 B 的版本暂时不变。