
이 문서에서는 다음을 가정함
- 현재 local repository는 remote repository에 submodule을 추가하기 전에 clone된 상태임.
- 이 local repository에서 remote repository의 submodule등을 반영하기 위한 절차를 설명한다.
1. 현재 상황.
- 현 local repository는 이전에 git clone으로 생성된 것임.
- 예:
~/workspace/myproj(이를 parent repository라고 부름: submodule에 대해)
이 local repository가 바라보는 remote repsoitory에서 다음의 경로에 submodule이 새로 추가됨
- 예:
lib/mylib
이를 local repository에서 반영하고자 함.
참고: 이미 submodule가 있는 상태(init은 이루어짐)에서 최신상태로 갱신만 필요한 경우
만약 이미 local repository에 submodule이 적용되어 있는 상태(이전에 init이 된 상태)에서
submodule의 최신 commit을 적용하는 경우라면 다음의 명령어로 충분함.
# parent repository로 이동
cd ~/workspace/myproj
# submodule의 최신 커밋 가져오기
git submodule update --remote --merge
# --init 을 사용하는 경우, parent repository가 참조하는 submodule의 commit으로 동기화.
# 현재 parent repository가 참조하는 submodule의 commit 확인은
# git ls tree <submodule의_상대경로> 를 사용
# 실행하는 위치에 따른 <submodule의_상대경로> 를 넣어주면 확인 가능: 2-7절 확인할 것
# commit pointer가 변경된 submodule 반영
git add lib/mylib
git commit -m "Update submodule to latest commit
- 이 방식은
.gitmodules에 모든 submodule들을 한번에 처리함.- .gitmodules에 등록된 각 submodule에 대해
- 지정된 remote 브랜치(branch = xxx)에서
- 최신 commit을 fetch.
- 현 submodule 디렉토리에 merge (or fast-forward) 반영함.
.gitmodules의 각 submodule에branch가 지정되어야 명시적으로 정확히 동작.- 없는 경우,
origin/main또는origin/master브랜치 처럼origin/HEAD가 가리키는 branch를 사용.
- 없는 경우,
- 3,4 번째 줄과 git add 와 commit을 통해 parent repository에도 변경을 기록: commit pointer (SHA1) 변경 기록.
submodule의 branch가 명확하지 않으면 다음으로 확인할 것:
# submodule의 디렉토리로 이동.
cd lib/mylib
# 원격 origin의 branch 확인.
git remote show origin
- parent repository (=main repository)의 root directory에 있는 .gimodules 에 기재된 경우가 대부분인.
만약, submodules의 각각의 디렉토리에서 pull을 하여 수동으로 업데이트를 따로 했다면,
(즉, 각 submodule 별로 따로 업데이트를 한 경우를 의미함)
parent respository에 해당 변경된 commit 에 대한 pointer를 갱신하도록 다음 을 수행한다.
# parent repository로 이동
cd ~/workspace/myproj
git add lib/mylib # submodule 디렉토리를 add하여 staging.
git commit -m "Update submodule to latest commit"
2. submodule을 추가 및 반영하기 위한 처리순서
2-1. parent repository 의 root directory로 이동.
cd ~/workspace/myproject
- 바로 .gitmodules 가 존재함.
2-2. 최신 변경사항 가져오기.
submodule이 추가되면서 생긴 .gitmodules를 가져오기 위한 단계.
git pull --recurse-submodule
.gitmodules와 submodule 경로에 대한 gitlink가 local repository에 반영됨.--recurse-submodules은 기존에init가 되어있는 submodule 들을 갱신하는 옵션임.- 이전에 init한 submodule이 없는 경우엔 필요없음.
- 이 문서가 가정한 현재 상황은 새로운 submodule이 remote repository에만 추가된 상황이므로 필요.
2-3. 실제 submodule (gitlink) 디렉토리 초기화 및 clone
앞서의 단계는 parent repository에 .gitmodules만을 가져온 것으로 아직 실제 submoduel의 디렉토리 등이 없음.
이 역시 일종의 저장소이므로 init을 해야만 함.
git submodule update --init --recursive
.gitmodules에 정의된 submodule의 정보를 바탕으로 실제 directory를 clone수행.- 실제로는 submodule의 remote repository를 clone 하는 것임.
- --init 는 현재 parent repository가 참조하는 submodule의 commit 을 가져옴.
- --update 의 경우엔 submodule저장소의 해당 브랜치의 최신 commit 을 가져옴.
--recursive는 netsted submodule까지 재귀적으로 처리함을 의미함.git submodule update에 의해 생성된 상태는detached HEAD임.- parent repository에서는 submodule을 해당 프로젝트의 특정 commit으로 고정시키는게 기본임.
- detached HEAD 를 유지하는 경우는 parent repository에서 해당 submodule을 사용만 할 뿐,
- 변경 및 수정을 하지 않는 경우에는 그냥 두어도 상관없음 (오히려 안전)
- 이는 해당 submodule의 프로젝트의 branch와 연결되어 있지 않으므로 add 나 commit을 해선 안됨
- 즉, submodule 원격 저장소의 내용을 그대로 쓰기만 하는 상태임.
- parent repository에서는 submodule을 해당 프로젝트의 특정 commit으로 고정시키는게 기본임.
detached HEAD 상태 해제를 해서 parent repository에서 submodule 디렉토리 내의 파일 수정을 submodule의 저장소에 반영하고 싶다면 다음을 진행.
2-4. 실제 submodule의 directory로 이동
cd lib/mylib
2-5. submodule의 detached HEAD상태 해제를 위한 branch 전환.
git switch main # or master 등의 실제 사용하는 branch)
- 다시한번 애기하지만,
submodule update로 내려온 상태는 보통detached HEAD임. git switch를 통해 branch로 전환해줘야 함.- submodule 프로젝트의 remote repository에 있는 branch를 지정함 (parent repository의 branch 아님)
- submodule의 디렉토리에서
git branch -r을 통해 가능한 remote branch 들의 list로 확인 후 지정하면 보다 안전함.
현재 parent repository의 submodule에서 참조하고있는 branch는 다음으로 확인 가능하니,
이를 확인하고 해당 branch로 switch하는것이 좋음:
git config -f ../../.gitmodules --get submodule.lib/mylib.branch
- 위에서 ../../ 는 현재 위치에서 parent repository의 root directory를 가리키는 상대 경로임: 그냥 에디터로 확인해도 되긴함.
- 이는
.gitmodules파일에서 해당 submodule에branch=...항목의 값을 출력함. .gitmoduels파일의branch항목은git submodule update --remote시 해당 branch를 대상으로 처리되게 함.
현재 .gitmodules에 지정된 branch가 없을 수도 있음.
이 경우엔 프로젝트에 맞게 branch를 지정(위의 switch한 브랜치임)하고, .gitmodules파일에 다음과 같이 추가해줌.
[submodule "lib/mylib"]
path = lib/mylib
url = https://github.com/example/mylib.git
branch = main # 사용하는 branch를 정확히 기재.
이후 parent repository(상위저장소, 메인저장소)의 root로 이동하여 다음을 수행.
git submoduel sync
.gitmodules의 파일 내용을 읽어서.git/config의 파일에서 submodule 관련 설정을 동기화함.
다음의 명령어로 확인하여 같아야만 함 (parent repository의 root directory에서 수행한 것임).
git config -f .gitmodules --get submodule.lib/mylib.branch
git config --get submodule.lib/mylib.branch
- 다르다면,
git submodule sync로.gitmodules내용으로.git/config파일을 동기화할 것.
2-6. submodule의 최신 commit가져오기.
git pull
- submodule의 remote repository의 해당 branch의 최신 commit을 가져옴.
git switch는 branch만을 변경할 뿐, 해당 branch의 최신 commit을 가져오지 않음.
2-7. parent repository에 submodule의 commit상태를 반영.
# parent repository에 속한 경로로 이동
# submodule 에 속한 directory만 아니면 됨.
cd ../../
git add lib/mylib
git commit -m "Update submodule to latest commit"
- parent repository는 submodule의 내용은 저장하지 않으나,
- submodule의 commit pointer는 저장하기 때문에
- 이를 반영해야 함.
submodule은 parent repository에서 또 다른 git repository를 참조하는 방식이기 때문에,
parent repository는 submodule에 대해 다음의 정보만을 저장 및 추적 관리함.
- submodule 의 parent repository내의 디렉토리 경로 및 URL (예:
lib/mylib)- 이는
.gitmoduels파일에 저장됨.
- 이는
- 해당 submoduel 이 가리키는 commit의 SHA (=pointer)
- git tree 에 저장됨. (
git ls-tree HEAD lib/mylib로 확인 가능)
- git tree 에 저장됨. (
2-8. 다음으로 submodule 에서 바뀐 commit을 확인 가능함.
git log -p --submodule
- -p : --patch 를 의미하며, commit의 변경사항(diff)를 함께 표시 (출력이 보통 길게 나오므로 pager 이용할 것)
- git log -p --submodule | less 와 같이 페이저로 읽어야 편함(나가려면 :q)
- --submodule : 출력에 submodule 관련 부분에 특별히 Submodule 이라는 단어로 시작하게 표시를 함.
- 단, parent repository에서 수행해야 함.
2024.01.30 - [utils/git and github] - [git] git message 확인 방식: pager 사용여부 설정
[git] git message 확인 방식: pager 사용여부 설정
pager.branch truepager를 사용할 경우,message가 마치 man page를 띄운 것처럼 따로 보여지게 된다.기본으로 less를 사용함.이렇게 보는 것이 편한 경우도 있지만, 내용을 확인하고 q를 입력하여 닫고 난 이
ds31x.tistory.com
2023.09.30 - [Linux] - [Linux] 파일 내용확인하기: cat, bat, less, more, head, tail
[Linux] 파일 내용확인하기: cat, bat, less, more, head, tail
cat, bat, head, tail대표적인 text processing utilities로 file viewing commands라고도 불림.less, morepager라고 불리는 utilities로 긴 출력을 화면에 페이지 단위로 나누어 보여주는 역할을 수행함.cat, batcat (concatenate
ds31x.tistory.com
같이보면 좋은 자료들
2024.05.20 - [utils/git and github] - [Git] Git Summary (작성중)
[Git] Git Summary (작성중)
git이란2024.05.20 - [utils/git and github] - Git : 소개 git 설치 후 해줘야 하는 작업들[Git] git 설치 후 우선 해줘야 하는 작업들 (tistory.com)local repository 초기화2024.05.20 - [utils/git and github] - [Git] init : local repo
ds31x.tistory.com
'utils > git and github' 카테고리의 다른 글
| git difftool 과 git mergetool (1) | 2025.07.22 |
|---|---|
| SSH Agent 사용법 (2) | 2025.07.21 |
| [git] How to Add a New Remote Branch to Your Local Repository (0) | 2024.12.26 |
| [Git] rebase: Tutorial (0) | 2024.05.28 |
| [Git] pager 옵션 조정-상세 (0) | 2024.05.27 |