Skip to content

Instantly share code, notes, and snippets.

@egoing
Last active November 3, 2021 10:47
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save egoing/612bb75f2bca99cd1b377074c369c495 to your computer and use it in GitHub Desktop.
Save egoing/612bb75f2bca99cd1b377074c369c495 to your computer and use it in GitHub Desktop.

submodule이란?

모듈(라이브러리)를 버전관리하는 방법입니다.

용어

  • super module : 모듈을 사용하는 모듈
  • sub module : 슈퍼 모듈에 의해서 사용되는 모듈

어떤 문제를 해결하나?

  1. 서브 모듈은 독립적인 저장소를 가질 수 있어야 합니다.
  2. 서브 모듈은 다양한 슈퍼 모듈에 의해서 사용될 수 있어야 합니다.
  3. 슈퍼 모듈 내에서 서브 모듈의 버전에 접근 가능해야 합니다.
  4. 슈퍼 모듈 내에서 서브 모듈은 다양한 이름의 디렉토리로 존재 할 수 있어야 합니다. (lib, common, module..)
  5. 슈포 모듈 내에서 서브 모듈의 특정 버전을 체크아웃 할 수 있어야 합니다.

시나리오

테스트 환경 만들기

git init sub1
cd sub1
touch 1
git add .; git commit -m "sub1 - 1"
cd ..

git init sub2
cd sub2
touch 1
git add .; git commit -m "sub2 - 1"
cd ..

git init super; 
cd super;
git submodule add ../sub1 lib1 # 서브 모듈과 다른 이름의 디렉토리에 연결할 수 있다.
git submodule add ../sub2 lib2

실습

git status 
  • .gitmodules에는 super의 디렉토리와 sub의 저정소 연결정보가 기록된다.
  • lib1, lib2에는 sub 저장소의 마지막 버전이 연결된다.
Changes to be committed:
  (use "git rm --cached <file>..." to unstage)
        new file:   .gitmodules => submodule의 저장소 정보
        new file:   lib1 => submodule의 마지막 버전 정보
        new file:   lib2
git diff --cached
diff --git a/.gitmodules b/.gitmodules
new file mode 100644
index 0000000..70e5265
--- /dev/null
+++ b/.gitmodules
@@ -0,0 +1,6 @@
+[submodule "lib1"]
+       path = lib1
+       url = ../sub1
+[submodule "lib2"]
+       path = lib2
+       url = ../sub2
diff --git a/lib1 b/lib1
new file mode 160000
index 0000000..b1a0cf7
--- /dev/null
+++ b/lib1
@@ -0,0 +1 @@
+Subproject commit b1a0cf7495d30ebf9e4b892b430462d81eb93997
diff --git a/lib2 b/lib2
new file mode 160000
index 0000000..6256fb8
--- /dev/null
+++ b/lib2
@@ -0,0 +1 @@
+Subproject commit 6256fb8df66bbd43d7b4120d8593b4e1d1d2334e
  • 커밋을 통해서 .submodule과 lib1, lib2를 버전으로 저장해서 연결이 지속되도록 한다.
git commit -am "sub module 연결"

서브 모듈의 변경사항을 슈퍼 모듈에 업데이트 하기 1

  • 서브모듈을 변경
cd .. 
cd sub1 
mv 1 2 
git add 2 
git commit -am "sub1 - 2"
cd ..
  • 슈퍼모듈에서 업데이트하기
cd super
git pull # sub1 을 해도 sub1은 업데이트 되지 않는다.
cd lib1
git pull # sub1이 업데이트 된다. 
  • lib1에 마지막으로 동기화된 버전을 확인
cd ..
git status
$ git status
On branch master
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git restore <file>..." to discard changes in working directory)
        modified:   lib1 (new commits)
  • lib1과 연결된 sub1을 고정한다.
git commit -am "update sub1 - 2"

서브 모듈의 변경사항을 슈퍼 모듈에 업데이트 하기 2

  • sub 모듈을 커밋한다.
cd ../sub1
mv 2 3
git add 3
git commit -m "sub1 - 3"
cd ../super
cd ../sub2
mv 1 2
git add 2
git commit -m "sub2 - 2"
cd ../super
  • 모든 서브 모듈을 한방에 업데이트 한다.
git submodule update --remote
  • 커밋하지 않은 서브 모듈의 상태를 보여준다.
git submodule summary
  • 커밋한다.
git commit -am "update sub1 - 3, sub2 - 2"
  • 서브 모듈에 일괄적으로 명령을 내린다.
git submodule foreach "git log --oneline; ls -al"
  • 슈퍼 모듈을 복제한다.
  • lib1과 lib2가 비어있는 것을 확인한다. => 불필요한 서브모듈은 복제를 하지 않기 때문에 저장공간을 아낄 수 있다.
cd ..
git clone super super2
cd super2
  • 서브 모듈을 선택적으로 연결한다.
git submodule init lib1
  • .submodule는 모든 서브 모듈에 대한 정보가 담겨 있다.
  • git submodule init은 모든 서브모듈을 가져온다.
  • .git/config 에는 현재 저장소에서 사용할 서브 모듈에 대한 정보만 담겨 있다.
cat .submodule
[submodule "lib1"]
        path = lib1
        url = ../sub1
[submodule "lib2"]
        path = lib2
        url = ../sub2
cat .git/config
cat .git/config
[submodule "lib1"]
        active = true
        url = /sub1
  • git submodule update로 서브 모듈의 내용을 업데이트해야 내용이 추가 된다.
  • 서브 모듈 연결 끊기 git submodule deinit SUBMODULE_DIR을 실행하면 디렉토리가 init 하기 전 상태가 된다.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment