지옥에서 온 Git

branch 병합 시 충돌해결

수업내용

여기서는 branch를 병합 할 때 git이 자동으로 처리해주는 소중한 작업이 무엇인가를 소개하고, 자동으로 병합할 수 없는 경우에는 어떻게 이를 수동으로 처리해야 하는지를 소개해드립니다. 

수업

수업내용

충돌이 일어났을 때 

충돌이 생기면 아래와 같은 메시지가 뜹니다. 

git status를 하면 충돌이 일어난 파일을 찾을 수 있습니다. 

 충돌이 발생한 파일을 수정합니다. 아래와 같습니다. 

'<<<<<<< HEAD' 부터 '=======' 사이의 구간이 현재 체크 아웃된 파일의 내용이고 '=======' 부터 '>>>>>>> exp' 사시의 구간이 병합하려는 대상인 exp 브랜치의 코드 내용입니다.  이 정보를 참고로해서 두개의 코드를 병합한 후에 특수기호들을 제거해주시면 됩니다. 작업이 끝나면 파일을 저장.

충돌 작업을 끝냈다는 것을 깃에게 알려줍니다. 

git add 'conflicted file name'

 

댓글

댓글 본문
  1. 20210613
  2. 박병진
    2021.02.10 완료
  3. supernet
    완료!!!
  4. 맥검
    덕분에 엉켜있던 문제를 해결했습니다. 감사합니다.
  5. 게케게케
    감사합니다 ㅠ.ㅠ
  6. fish5542
    너무재밋쩡
  7. 초간단
    (지난상태)
    master : 1 - 2 - 5 - (병합)
    exp : \ 3 - 4 /

    (오늘의 결과상태)
    master : 1 - 2 - 5 - (1병합) - 6 - (2병합) - - (3병합) - 9 - (4각자병합) - 11 - (5병합)
    exp : \ 3 - 4 / \ 7 / \ 8 / \ 10 - (4각자병합) - 12 /

    (1병합)->(2병합)
    master에서 master.txt 만들고 commit 6, exp에서 exp.txt 만들고 commit 7 생성.
    master에서 병합.
    배운점: exp의 파일을 master로 파일을 가져왓군

    (2병합)->(3병합)
    common.txt (내용은 function a() {}) 만들고, exp에서 commit 8 생성.
    master로 돌아와서 병합.

    (3병합)-> (4병합)
    master의 common.txt의 내용을
    function b() {}
    function a() {}
    로 수정하고, commit 9 생성.

    exp의 common.txt의 내용을
    function a() {}
    function c() {}
    로 수정하고, commit 10 생성.

    master에서 병합. ==>성공!(common.txt 내용 확인 시, 안의 내용이 병합됨을 확인함. 자동으로 합쳐줌)
    (common.txt내용)
    function b() {}
    function a() {}
    function c() {}
    성공 후, exp에서도 병합해서 서로 똑같은상태로 만들어봅시다.

    (4병합) -> (5병합)
    master에서 common.txt파일 내의 a(master)로 ()안에 master써서 수정하고 commit 11생성.
    exp에서 common.txt파일 내의 a(exp)로 ()안의 내용 추가하여 수정하고 commit 12 생성.

    master에서 병합 ==> 실패(common.txt 내용에 안합쳐진다고 뜸. 수작업으로 해야함.)
    (우리가 쓴 코드를 적절히 바꿔서 수작업으로 바꿔준 후, 저장하고 add,commit 하면 됨)

    병합 실패시, git checkout도 안되는데, $git reset --merge 하면 실패에서 벗어날 수는 있음.(병합취소)
  8. PassionOfStudy
    merge를 할 때 발생하는 충돌현상
    같은 파일의 같은 부분을 각각의 branch에서 수정하고나서 merge하게 되면 충돌이 일어난다.
    git status 명령을 통해서 conflict된 파일을 확인하고 파일을 열어 수정한다.
    solve)
    <<<<<<< HEAD' 부터 '=======' 사이의 구간이 현재 체크 아웃된 파일의 내용이고 '=======' 부터 '>>>>>>> exp' 사이의 구간이 병합하려는 대상인 exp 브랜치의 코드 내용입니다. 이 정보를 참고로해서 두개의 코드를 병합한 후에 특수기호들을 제거하면 된다. 작업이 끝나면 파일을 저장한다.
  9. software.lee
    감사하빈다.
  10. Deuklyoung Ko
    커밋 하기 전까지는 해당 파일을 공유 하더 군요.

    해당 파일 커밋 하시면 커밋한 브랜치로 체크인 했을 때만 보일 겁니다.


    충돌 메세지는
    https://opentutorials.org......468
    여기서 설명해 주시네요.
    대화보기
    • devchun
      감사합니다 :)
    • 김경원
      브랜치 병합 동영상을 보면서 실습을 하던 도중에 특이한 오류(?)가 생겼습니다.

      브랜치를 병합 하고 충돌이 일어났을 때의 오류가 저도 같이 떳었습니다. (master 시점) 그래서 status로 확인을 해보니 use "git add <file>..." to include in what will be committed f2.txt 이렇게 떳길래 add를 해준 후 다시 병합을 해줬더니 자동으로 커밋이 되어 잘 되었습니다.

      그런데 exp 브랜치에서 파일을 하나 만들어 보았더니 master 에도 똑같은 파일이 생겼습니다.

      이상하다 싶어 파일들을 새로 만들어 보니 master에서 파일을 만들든 exp 에서 만들든 ls -al 로 파일 목록을 확인 해보니 두 브랜치 모두 파일을 생성할때마다 파일이 공존 되어 있었습니다.

      예) 병합 후 master에서 f4.txt 파일을 만들었더니 exp 브랜치일때도 에도 파일이 있음 , exp로 체크아웃 후 exp 에서 f5.txt 파일을 만들었더니 master시점에서도 f5.txt 파일이 있음

      로그 기록을 확인해 master에서 exp 브랜치를 병합 했을때 자동으로 커밋 된 부분을 보니 HEAD 가 exp , master 두개 더군요

      참고로 exp 에서 master를 병합할땐 자동으로 커밋이 되지 않았습니다.

      이후로 checkout 할때마다

      $ git checkout master
      Switched to branch 'master'
      A f4.txt
      A f5.txt
      A f6.txt


      이렇게 새로 만든 파일들 옆에 'A' 라고 뜨고 그럽니다.

      왜 이런 경우가 생긴거죠?
    • 황지현
      "지옥에서 온 Git" 강의를 보았던 개발자입니다.
      제가 블로그에 정리한 내용을 공유합니다^^

      gitlab, bitbucket, pull request, opensource contribution에 관심이 많으신 분은 도움이 되실거라고 생각합니다.
      제 블로그에 방문하셔서 많은 댓글 부탁드립니다.ㅎㅎ

      [TIP] git merge 정리 (vimdiff 사용)
      http://jhhwang4195.tistory.com......693
    • haMsa
      감사합니다.
    • 김수현
      [ 충돌 예방법 ]
      https://opentutorials.org......091 <-- SourceTree를 사용하여 Git 사용하는 방법 강의

      어차피 병합되는(병합당하는) 브랜치(예:exp브랜치)에서
      병합하는 브랜치(예:master브랜치)의 변화를 자주 병합하여 가져온다.
      (그러면 작은 충돌이 발생한다)
      그런데... 6개월쯤 긴 기간동안 한번도 병합을 해주지않다가 병합하면...
      (큰 충돌이 발생하고...해결하기 곤란해진다)

      병합당하는 브랜치에서 병합하는 브랜치의 내용을 자주 병합하여 가져오고
      그러면서 작업을 해야 한다.
    • 김수현
      깃이 얼마나 많은 부분을 자동화해주는가? 기특하다
      git branch exp
      git branch -d exp
      다시 만들어야 겠음
      합치지 않았는데 정말 지울 거냐?
      그러면 강제로 지워야 함
      git branch -D exp(55)
      git branch exp
      vim master.txt라는 파일을 만듬
      내용을 a라고 할 것임
      git add master.txt
      git commit -m "6"
      git checkout exp
      vim exp.txt > 내용은 a
      git add exp.txt
      git commit -m "7"
      git checkout exp
      vim common.txt
      파일안의 내용 변경 (exp)
      같은 곳을 변경... 뭔가 문제가 심각해짐
      같은 부분을 수정하고 병합하면 에러남
      그리고 커밋 12
      git checkout master
      git merge exp
      컨프릭트 에러남
      git status
      언 머지드 패스라도 나옴
      커먼.txt가 양쪽에서 바뀜 나옴
      vim common.txt
      그러면 새로운 내용이 나옴
      기호를 해석할 수 있는 능력이 있어야 함
      ============
      여러분에게 충돌해결을 위임한 것임
      동시에 가지고 있는 것으로 하고
      다른 것은 삭제함
      git add common.txt
      git status
      git commit
      :wq
      git log
      vim common.txt
      컨플릭트가 나면 이런식으로 처리하면 됨


      위 내용을 정리하면...
      common.txt <---mater와 exp에서 같은 부분을 고쳤음(다른 내용으로)
      그리고 머지를 하면 ... 고친부분(같은 부분이지만 다르게 고쳐서)에서 컨프릭에러가 남
      그 에러난 파일에 vim common.txt로 들어가면...
      ===============(이와 같은 선을 기준으로 위, 아래로 같은 부분에서 다르게 처리한 부분이 나옴(위에 있는 그림 참조))
      그러면 그 부분을 삭제할 것은 삭제하고 남길 것은 남기고 적절히 해결해서 수정한 후에
      '애드 파일명'(<--- 컨플릭트를 처리했다고 알려주는 것임)와 커밋(커밋 이름 주지 않고)함 >에디터 안에 들어가면 (병합처리 완료했다라는)메시지 나옴 > :wq > 문제 해결됨

      더 간단히 설명하면
      컨플릭트가 난 파일을 ---> 파일편집기를 사용하여 컨플릭트문제 수정 --->
      add 파일명(문제해결했다고 알리는 것임)하고 --> 커밋 ===> 문제해결됨
      https://www.slideshare.net......752 <--42P참조
    • groundntree
      * 브랜치 만들기
      git branch -b exp
      git branch

      << 충돌이 발생하지 않는 경우의 병합 실습 >>

      1. 서로 다른 파일을 작업하는 경우
      * master 브랜치에서 master.txt 생성후 커밋
      git checkout master
      vim master.txt
      git add master.txt
      git commit -m "6"

      * exp 브랜치에서 exp.txt 생성후 커밋
      git checkout exp
      vim exp.txt
      git add exp.txt
      git commit -m "7"

      * 병합
      git checkout master
      git merge exp
      git log --branches --graph --decorate
      ls -al

      2. 같은 파일의 다른 부분을 추가할 경우

      * exp 브랜치에서 common.txt 에 function a() {} 를 만드세요.
      git checkout exp
      vim common.txt
      git add common.txt
      git commit -m "8"

      * master 브랜치에서 common.txt 에 function b() {} 를 만드세요.
      git checkout master
      git merge exp
      ls -al
      vim common.txt
      git commit -am '9'

      * exp 브랜치에서 common.txt 에 function c() {} 를 만드세요.
      git checkout exp
      vim common.txt
      git commit -am "10"

      * master 브랜치에서 exp 브랜치를 병합합니다.
      git checkout master
      git merge exp
      ls -al
      vim common.txt
      cat common.txt

      * exp 브랜치에서 master 브랜치를 병합합니다.
      git checkout exp
      cat common.txt
      git merge master
      cat common.txt

      << 충돌이 발생할 경우의 실습 >>

      * master 브랜치에서 common.txt 의 function b(master)로 수정 후 커밋
      git checkout master
      vim common.txt
      git commit -am '11'

      * exp 브랜치에서 common.txt 의 function b(exp)로 수정 후 커밋
      git checkout exp
      vim common.txt
      git commit -am '12'

      * master 브랜치에서 exp 브랜치를 병합하면 충돌이 발생합니다.
      git checkout master
      git merge exp
      git status

      * 충돌이 발생한 파일을 다시 수정하여 커밋합니다.
      vim common.txt
      git add common.txt
      git status
      git commit
      git log
      cat common.txt
    • seulcode
      항상 좋은 수업 감사드립니다. 깃의 세계에 빠져들고 있네요...

      아래쪽 텍스트 에서 >>>>exp' 사시의 -> 사이의 오타인것 같습니다!
      항상 감사드립니다 이고잉님... 나중에 저도 오픈소스로 보은하겠습니다.