깃 그래프를 보면 파란색 branch가 중간에 끊겨있다.
위와 같은 Git Graph를 본 적 있으신가요?
아직 깃허브 사용이 미숙한 초보 AI개발자들끼리 협업을 하다보니 Branch를 생성할 때 Main에서 Pull 혹은 Clone 하지 않고 개인 별로 Branch를 먼저 파서 각자의 코드로 프로젝트를 진행하다보니 프로젝트 종료 후에 코드 정리 과정에서 어려움이 발생했습니다.
그래서 이런 어려움이 발생한 원인과 해결 과정을 정리해 앞으로의 어려움을 줄여보고자 합니다.
pull -> checkout -> 수정 -> commit -> push 가 일반적인 github를 활용한 코드 작성 법 입니다. 그러나 저는 오늘 아무생각 없이 디버깅만 생각하고 pull -> 수정 -> commit 후에 push를 시도했습니다. 그 결과 아래와 같은 오류를 마주쳤습니다.
error: src refspec donghun does not match any
확인해보니 push를 해야하는 branch는 remote branch인데 local branch인 master에서 코드 수정이 commit 된 것 이었습니다. 이 때 header가 remote branch에서 떨어져 있는 detach되어 있는 상태임을 확인했습니다. 구글링을 해보니 이렇게 서로 commit이 다른 branch끼리 merge를 통해 간단히 해결할 수 있음을 알게 되었습니다.
git checkout <remote branch>
코드 수정이 반영되야하는 remote branch로 checkout 해주고,
git merge <local branch>
local branch로 merge 해주면 remote branch가 local branch의 최근 commit의 변화를 반영하게 되고, header와 remote branch가 연결된 상태가 됩니다. 이 상태에서 push해주면, 우리가 원하는 수정사항이 반영되어 remote에 저장됩니다.
1의 과정을 거친 뒤 remote branch를 main branch에 merge 하는 과정에서 또 한 번의 오류가 발생했습니다.
우선 호기롭게 main과 branch의 merge를 시도했습니다.
git merge origin main
그러나 merge: origin - not something we can merge 라는 오류 메세지를 받고 거절 당했습니다. local은 main이 뭔지 모르는게 당연합니다. 한번도 불러온적도, 연결한 적도 없기 때문입니다. 그래서 main을 pull 해보기로 했습니다.
git pull origin main
git의 대답은 아래와 같았습니다.
main을 pull을 하라고 하면 3개의 옵션 중에 하나를 선택해서 하라고 나옵니다.
1. git config pull.rebase false
2. git config pull.rebase true
3. git config pull.ff only
3가지의 옵션이 어떤 의미인지 살펴보고 저에게 필요한 선택지를 골라보겠습니다.
쉽게 말하면 커밋의 기록을 바꿔주는 기능입니다.
rebase기능을 활용하면 두개의 branch가 마치 한개의 branch 였던 것 처럼 선형의 히스토리로 남깁니다. 이 때 주의할 점은 히스토리를 하나로 합치는 과정에서 작업했던 것을 다시 해야하는 상황이 발생할 수 있습니다.
rebase true: pull할 때 rebase 옵션이 적용돼 커밋 히스토리가 깔끔해지고 merge 커밋이 생성되지 않습니다.rebase false: pull할 때 rebase 옵션이 적용되지 않아 merge 커밋이 생성됩니다.ff only는 fast-forward 병합만 허용되도록 하는 옵션입니다.
fast-forward 병합이란 현재 브랜치가 병합 대상 브랜치의 최신 commit을 포함하고 있을 때 일어나는 병합입니다. 이 경우에 git은 추가적인 merge commit을 생성하지 않고 현재 브랜치를 최신 커밋으로 이동시킵니다.
저는 서로 commit 이력이 다른 두개의 branch를 merge하기 위한 연산을 선택해야 하기 때문에
git config pull.rebase false
위의 명령어를 통해 pull을 해주었습니다. 그러자 main이 성공적으로 pull이 되었고, merge 과정에서 발생하는 conflict를 해결해주자 성공적으로 merge가 되었습니다.