应用场景

在项目中引用第三方库或者在模块化开发中,某些公共的模块是需要单独维护。

环境准备

初始两个测试仓库

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#先创建两个目录,模拟git server端和工作目录
mkdir -p test-submodule/{server,client}

cd test-submodule/server
#初始化两个git仓库
git init --bare project-main
git init --bare project-sub

#切到工作目录,git clone两个仓库,添加一些测试文件
cd ../client
git clone ../server/project-main
echo "this main project" > main.test
git add -A && git commit -m "test" && git push

cd ../client
git clone ../server/project-sub
echo "this sub project" > sub.test
git add -A && git commit -m "test" && git push

➜  project-sub git:(master) ✗ git add -A && git commit -m "test" && git push
[master (root-commit) 9b6a096] test
 1 file changed, 1 insertion(+)
 create mode 100644 sub.test
Enumerating objects: 3, done.
Counting objects: 100% (3/3), done.
Writing objects: 100% (3/3), 219 bytes | 219.00 KiB/s, done.
Total 3 (delta 0), reused 0 (delta 0)
To /Users/xnile/Downloads/test-submodule/client/../server/project-sub
 * [new branch]      master -> master

测试添加 submodule

进入project-main目录 ,添加project-sub子目录,模拟主项目中要引入公共模块。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
cd ../project-main
git remote -v
origin	/Users/xnile/Downloads/test-submodule/client/../server/project-main (fetch)
origin	/Users/xnile/Downloads/test-submodule/client/../server/project-main (push)

#添加子模块
git submodule add ../../server/project-sub
Cloning into '/Users/xnile/Downloads/test-submodule/client/project-main/project-sub'...
done.

#查看当前目录,验证子模块已添加到当前目录
(py3) ➜  project-main git:(master) ✗ ls -l
total 8
-rw-r--r--  1 xnile  staff   18 Dec  3 09:17 main.test
drwxr-xr-x  4 xnile  staff  128 Dec  3 09:30 project-sub

#子模块的信息记录在git配置文件
cat .git/config
[submodule "project-sub"]
	url = /Users/xnile/Downloads/test-submodule/client/../server/project-sub
	active = true

#提交更改到master
git add -A;git commit -m "add submodule";git push

git clone 拉取带有子目录的仓库

  • git clone 的时候带上--recursive参数

    1
    2
    3
    4
    5
    6
    7
    
    (py3) ➜  temp git clone --recursive  ../../server/project-main
    Cloning into 'project-main'...
    done.
    Submodule 'project-sub' (/Users/xnile/Downloads/test-submodule/client/temp/../../server/project-sub) registered for path 'project-sub'
    Cloning into '/Users/xnile/Downloads/test-submodule/client/temp/project-main/project-sub'...
    done.
    Submodule path 'project-sub': checked out '9b6a0963e0e379f624ce71c6c257acf938232423'
    
  • git submodule update –init –recursive

    如果git clone的时候没有加上--recursive也没关系,我们先clone 主项目后,再执行上边命令。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    
    (py3) ➜  temp2 git clone ../../server/project-main
    Cloning into 'project-main'...
    done.
    (py3) ➜  temp2 cd project-main
    (py3) ➜  project-main git:(master) git submodule update --init --recursive
    Submodule 'project-sub' (/Users/xnile/Downloads/test-submodule/client/temp2/../../server/project-sub) registered for path 'project-sub'
    Cloning into '/Users/xnile/Downloads/test-submodule/client/temp2/project-main/project-sub'...
    done.
    Submodule path 'project-sub': checked out '9b6a0963e0e379f624ce71c6c257acf938232423'
    

参考

https://git-scm.com/book/zh/v2/Git-%E5%B7%A5%E5%85%B7-%E5%AD%90%E6%A8%A1%E5%9D%97