병합 충돌

Tier: Free, Premium, Ultimate Offering: GitLab.com, Self-managed, GitLab Dedicated

병합 충돌은 병합 요청에서 두 브랜치(소스 및 대상)가 서로 다른 변경 사항을 가질 때 발생합니다. 어떤 변경을 수용할지 결정해야 합니다. 병합 요청에서 Git은 두 파일 버전을 한 줄씩 비교합니다. 대부분의 경우, GitLab은 변경 사항을 함께 병합할 수 있습니다. 그러나 두 브랜치가 동일한 줄을 변경하는 경우 GitLab은 병합을 차단하고, 어떤 변경을 유지할지 선택해야 합니다:

병합 충돌로 인해 차단된 병합 요청

충돌이 있는 병합 요청은 다음 중 하나를 수행할 때까지 병합할 수 없습니다:

  • 병합 커밋을 생성합니다.
  • 리베이스를 통해 충돌을 해결합니다.

GitLab은 소스 브랜치에 병합 커밋을 생성하여 충돌을 해결하지만, 이를 대상 브랜치에 병합하지 않습니다. 그 후 병합 커밋을 검토하고 테스트할 수 있습니다. 의도치 않은 변경 사항이 없으며 빌드를 깨뜨리지 않는지 확인하세요.

충돌 블록 이해하기

Git이 충돌을 감지하고 귀하의 결정이 필요한 경우, 충돌 블록의 시작과 끝을 충돌 마커로 표시합니다:

  • <<<<<<< HEAD는 충돌 블록의 시작을 나타냅니다.
  • 귀하의 변경 사항이 표시됩니다.
  • =======는 귀하의 변경 사항 종료를 나타냅니다.
  • 대상 브랜치의 최신 변경 사항이 표시됩니다.
  • >>>>>>>는 충돌의 끝을 나타냅니다.

충돌을 해결할 때는 다음을 삭제합니다:

  1. 유지하고 싶지 않은 충돌 줄의 버전입니다.
  2. 충돌 마커 세 개: 시작, 끝, 및 두 버전 사이의 ======= 줄입니다.

사용자 인터페이스에서 해결할 수 있는 충돌

병합 충돌이 다음 모든 조건을 충족하는 경우, GitLab 사용자 인터페이스에서 충돌을 해결할 수 있습니다:

  • 파일은 텍스트 파일이어야 하며, 이진 파일이 아닙니다.
  • 파일은 UTF-8 호환 인코딩이어야 합니다.
  • 파일은 이미 충돌 마커를 포함하고 있지 않아야 합니다.
  • 추가된 충돌 마커가 있는 파일 크기는 200 KB 미만이어야 합니다.
  • 파일은 두 브랜치 모두에서 동일한 경로에 있어야 합니다.

병합 요청의 어떤 파일이 충돌을 포함하고 있지만 모든 기준을 충족할 수 없는 경우, 충돌을 수동으로 해결해야 합니다.

충돌 해결 방법

GitLab은 사용자 인터페이스에서 해결 가능한 충돌을 보여주며, 명령줄을 통해 로컬에서 충돌을 해결할 수도 있습니다:

  • 인터랙티브 모드: UI 방법으로, 충돌이 단순히 유지할 줄의 버전을 선택할 필요가 있을 때 가장 적합합니다.

  • 인라인 편집기: UI 방법으로, 줄을 편집하고 수동으로 변경 사항을 섞는 복잡한 충돌에 가장 적합합니다.

  • 명령줄: 가장 복잡한 충돌에 대한 완전한 제어를 제공합니다.

인터랙티브 모드에서

GitLab 사용자 인터페이스에서 덜 복잡한 충돌을 해결하려면:

  1. 왼쪽 사이드바에서 검색 또는 이동을 선택하고 프로젝트를 찾습니다.

  2. 코드 > 병합 요청을 선택하고 병합 요청을 찾습니다.

  3. 개요를 선택하고 병합 요청 보고서 섹션으로 스크롤합니다.

  4. 병합 충돌 메시지를 찾아 충돌 해결을 선택합니다.
    GitLab은 충돌이 있는 파일 목록을 표시합니다. 충돌하는 줄은 강조 표시됩니다:

    충돌 섹션

  5. 각 충돌에 대해 우리 것을 사용 또는 그들의 것을 사용을 선택하여 유지할 충돌 줄의 버전을 표시합니다. 이 결정은 “충돌 해결”로 알려져 있습니다.

  6. 모든 충돌을 해결했으면 커밋 메시지를 입력합니다.

  7. 소스 브랜치에 커밋을 선택합니다.

충돌을 해결하면 병합 요청의 대상 브랜치가 소스 브랜치에 병합되며, 선택한 텍스트 버전을 사용합니다. 소스 브랜치가 feature이고 대상 브랜치가 main이라면, 이러한 작업은 로컬에서 git switch feature; git merge main을 실행하는 것과 같습니다.

인라인 편집기에서

일부 병합 충돌은 더 복잡하며, 충돌을 해결하기 위해 수동으로 줄을 편집해야 합니다. 병합 충돌 해결 편집기는 GitLab 인터페이스에서 이러한 복잡한 충돌을 해결하는 데 도움을 줍니다:

  1. 왼쪽 사이드바에서 Search or go to를 선택하고 프로젝트를 찾습니다.

  2. Code > Merge requests를 선택하고 병합 요청을 찾습니다.

  3. Overview를 선택하고 병합 요청 보고서 섹션까지 스크롤합니다.

  4. 병합 충돌 메시지를 찾아 Resolve conflicts를 선택합니다.
    GitLab은 병합 충돌이 있는 파일 목록을 표시합니다.

  5. 수동으로 편집할 파일을 찾아 충돌 블록까지 스크롤합니다.

  6. 해당 파일의 헤더에서 Edit inline을 선택하여 편집기를 엽니다. 이 예에서는 충돌 블록이 1350번째 줄에서 시작하여 1356번째 줄에서 끝납니다:

    Merge conflict editor

  7. 충돌을 해결한 후 Commit message를 입력합니다.

  8. Commit to source branch를 선택합니다.

명령줄에서

대부분의 충돌은 GitLab 사용자 인터페이스를 통해 해결할 수 있지만, 일부는 너무 복잡합니다. 복잡한 충돌은 각 변경 사항에 대한 가장 많은 제어를 제공하기 위해 로컬에서 명령줄을 통해 수정하는 것이 좋습니다.

사전 요구 사항:

  • 브랜치에 강제 푸쉬할 수 있는 권한이 있어야 합니다.
  1. 터미널을 열고 기능 브랜치를 체크아웃합니다. 예를 들어, my-feature-branch:

    git switch my-feature-branch
    
  2. 브랜치를 재조정하여 Git이 충돌을 알리도록 대상 브랜치(여기에서는 main)에 대해 재조정합니다:

    git fetch
    git rebase origin/main
    
  3. 선호하는 코드 편집기에서 충돌 파일을 엽니다.

  4. 충돌 블록을 찾습니다.

  5. 파일을 편집합니다:
    1. 유지할 버전(======= 이전 또는 이후)을 선택합니다.
    2. 유지하고 싶지 않은 버전을 삭제합니다.
    3. 충돌 표시기를 삭제합니다.
  6. 파일을 저장합니다.

  7. 충돌 항목이 포함된 각 파일에 대해 이 과정을 반복합니다.

  8. Git에서 변경 사항을 스테이징합니다:

    git add .
    
  9. 변경 사항을 커밋합니다:

    git commit -m "Fix merge conflicts"
    
  10. 재조정을 계속합니다:

    git rebase --continue
    

    경고:
    이 시점까지는 git rebase --abort를 실행하여 프로세스를 중단할 수 있습니다.
    Git은 재조정을 중단하고 브랜치를 이전 상태로 롤백합니다.
    git rebase --continue를 실행한 후에는 재조정을 중단할 수 없습니다.

  11. 변경 사항을 원격 브랜치에 강제 푸쉬합니다.

관련 주제