[Git] git merge and conflict

su_y2on·2022년 3월 17일
0

Git

목록 보기
2/2
post-thumbnail
post-custom-banner

git merge and conflict

작업이 커지면 master에서 따로 브랜치를 빼서 처리를 하게됩니다. 처리가 끝난뒤에 다시 master브랜치에 merge를 해서 내용을 합치곤 하는데요. 이때 같은 파일에 같은 line에 대해 수정사항이 겹치거나 수정된 파일을 지우는 상황이 발생하면 git에서 자동으로 합쳐주지 못하고 conflict를 냅니다.

사실 conflict가 애초에 안나도록 소통을 원할하게 하는 것이 중요하지만 여러명이 프로젝트를 하거나 프로그램이 커지면 conflict는 흔히 발생하는 일입니다. 따라서 해결방법을 아는 것이 중요합니다! 간단한 예제로 conflict를 낸뒤에 해결해보도록 하겠습니다~



1. master에 내용 작성하고 commit하기

# master branch에 파일작성하기 
suy2on@YEONui-MacBookPro merge % vi 1.txt
suy2on@YEONui-MacBookPro merge % cat 1.txt
this is merge and conflict test file
this line is written by master 
# commit
suy2on@YEONui-MacBookPro merge % git add .  
suy2on@YEONui-MacBookPro merge % git commit -m '1st commit in master'
[master (root-commit) 6f9c9a7] 1st commit in master
 1 file changed, 2 insertions(+)
 create mode 100644 1.txt



2. issue브랜치를 파서 같은 파일 수정하고 commit

# issue branch 파고 checkout 
suy2on@YEONui-MacBookPro merge % git branch issue
suy2on@YEONui-MacBookPro merge % git checkout issue
Switched to branch 'issue'

# 같은 파일 수정 
suy2on@YEONui-MacBookPro merge % vi 1.txt
suy2on@YEONui-MacBookPro merge % cat 1.txt
this is merge and conflict test file
this line is written by issue 

# commit
suy2on@YEONui-MacBookPro merge % git commit -am '1st commit in issue'
[issue 6ac6a1d] 1st commit in issue
 1 file changed, 1 insertion(+), 1 deletion(-)



3. master브랜치로 돌아와서 issue에서 수정한 같은 라인 수정하기

suy2on@YEONui-MacBookPro merge % git checkout master
Switched to branch 'master'

# master branch에서는 내용이 그대로입니다
suy2on@YEONui-MacBookPro merge % cat 1.txt
this is merge and conflict test file
this line is written by master 

# master branch에서 두번째 줄은 건들지 말라고 적겠습니다 
suy2on@YEONui-MacBookPro merge % vi 1.txt
suy2on@YEONui-MacBookPro merge % cat 1.txt
this is merge and conflict test file
this line is written by master, nobody can modify this line  



4. master branch에 issue branch merge하기

# 충돌발생 : 자동머지에 실패했다고 나오네요 아주자세하게 설명해줍니다!
suy2on@YEONui-MacBookPro merge % git merge issue
Auto-merging 1.txt
CONFLICT (content): Merge conflict in 1.txt
Automatic merge failed; fix conflicts and then commit the result.




5. 충돌파악

  1. git status : 아주 친절하게 충돌을 해결하고 git commit을 하라고 합니다. 또한 merge시도한 것을 아예 되돌리고 싶다면 git merge --abort를 하라고 알려줍니다. 그리고 1.txt파일에서 충돌이 났고 수정이 겹쳤기때문이라고 알려줍니다 (깃은 정말 친절해요👍)
On branch master
You have unmerged paths.
  (fix conflicts and run "git commit")
  (use "git merge --abort" to abort the merge)

Unmerged paths:
  (use "git add <file>..." to mark resolution)
	both modified:   1.txt



  1. 충돌난 파일 들어가보기 : 충돌이 난 파일은 아래와 같이 수정되어있습니다 바로 충돌이 난 부분을 자세히 알려주는 겁니다. 먼저 HEAD는 현재 checkout한 브랜치입니다. master겠죠? 거기서는 "this line is written by master, nobody can modify this line" 이랬던 문장이 issue 브랜치에서는 "this line is written by issue" 이렇다고 알려주네요!
suy2on@YEONui-MacBookPro merge % cat 1.txt
this is merge and conflict test file
<<<<<<< HEAD
this line is written by master, nobody can modify this line  
=======
this line is written by issue 
>>>>>>> issue




6. mergetool conflict 해결하기

mergetool을 이용해서 conflict를 해결해보도록 할게요!

보기좋게 충돌도 보여주고 또 고치기도 편합니다. mergetool은 여러종류가 미리설정을 해놓지 않았다면 선택하라는 입력이 뜹니다. 저는 그냥 vimdiff로 해줬습니다.

suy2on@YEONui-MacBookPro merge % git mergetool

This message is displayed because 'merge.tool' is not configured.
See 'git mergetool --tool-help' or 'git help config' for more details.
'git mergetool' will now attempt to use one of the following tools:
tortoisemerge emerge vimdiff
Merging:
1.txt

Normal merge conflict for '1.txt':
  {local}: modified file
  {remote}: modified file
Hit return to start merge resolution tool (vimdiff): vimdiff



이렇게 창이 하나 뜹니다. 이 창은 4개의 파일을 한번에 보여주고 있습니다. 먼저 크게 위쪽에 3개의 파일이 밑에 하나의 파일이 있습니다. 위쪽 3개는 왼쪽부터 LOCAL, BASE, REMOTE라고 적혀있네요.

흔히 git에서 쓰는 개념과는 다르게 BASE는 처음에 issue브랜치를 냈을 때 상태를 말해요. 즉 둘다 수정하기 전 상태입니다. 그리고 LOCAL은 현재 master브랜치로 merge를 최종적으로 하는쪽 파일입니다. REMOTE는 merge를 당하는 쪽인 issue브랜치의 파일입니다. 가장 아래파일은 최종적으로 merge할 파일의 내용입니다.

빨간색은 충돌이 난 부분이라고 보시면됩니다. 아래쪽에 최종 merge할 파일에서 먼저 충돌을 처리할 곳에 커서를 위치시킵니다.


그리고 <:diffg 선택할 상태의 앞두글자>를 적어주고 엔터를 치면 됩니다. 저는 master의 내용으로 결정하기위해 :diffg LO라고 해줬습니다. 그럼 바로 저렇게 master의 내용으로 선택되서 문서가 자동으로 바뀝니다.


이제 빠져나가기 위해 :wqa라고하고 나옵시다. 뒤에 a를 붙여주는건 4개의 파일을 한번에 저장하고 나오기위해서 입니다.




7. merge하기

충돌이 해결되었지만 아직 merge가 진행중이니 git commit을 하라고 합니다. commit후 log를 보니 merge가 제대로 됐네요🤗

suy2on@YEONui-MacBookPro merge % git status
On branch master
All conflicts fixed but you are still merging.
  (use "git commit" to conclude merge)

# commit하기 
suy2on@YEONui-MacBookPro merge % git commit -m "merge conpletion" 
[master 3fb240e] merge conpletion
suy2on@YEONui-MacBookPro merge % git log
commit 3fb240ef6e7770e6fcbf342f58455effada0884e (HEAD -> master)
Merge: 5c0493b 6ac6a1d
Author: suy2on <tnwjdrms@naver.com>
Date:   Fri Mar 18 02:06:14 2022 +0900

    merge conpletion



8. .orig파일

mergetool를 사용하면 .orig파일이 자동으로 생성됩니다. 이 파일은 수정하기전 파일을 보존해놓기위해 생성되는 것인데요. .gitignore에 넣어서 git이 추적하지 않게 하시거나 아래 명령어로 애초에 저 파일이 생성되지 않게 할 수 있습니다.

git config --global mergetool.keepBackup false
post-custom-banner

0개의 댓글