병합 요청 문제 해결

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

병합 요청 작업 중 다음과 같은 문제가 발생할 수 있습니다.

병합 요청이 파이프라인 상태를 검색할 수 없음

이는 Sidekiq가 변경 사항을 빠르게 처리하지 못할 때 발생할 수 있습니다.

Sidekiq

Sidekiq가 CI 상태 변경을 처리하지 못했습니다. 잠시 기다리면 상태가 자동으로 업데이트됩니다.

파이프라인 상태를 검색할 수 없음

병합 요청 파이프라인 상태는 다음이 발생할 때 검색되지 않을 수 있습니다:

  1. 병합 요청이 생성됨
  2. 병합 요청이 닫힘
  3. 프로젝트에서 변경이 이루어짐
  4. 병합 요청이 다시 열림

파이프라인 상태를 올바르게 검색하려면 병합 요청을 다시 닫고 열어주십시오.

레일스 콘솔에서 병합 요청 다시베이스로 변경

Tier: Free, Premium, Ultimate

/rebase 빠른 동작 외에 레일스 콘솔에 액세스할 수 있는 사용자는 레일스 콘솔에서 병합 요청을 다시베이스로 변경할 수 있습니다. <username>, <namespace/project>, <iid>를 적절한 값으로 대체하세요:

경고: 데이터를 직접 변경하는 모든 명령에는 올바르게 실행되지 않거나 적절한 조건에서 실행되지 않을 경우에는 피해를 줄 수 있습니다. 테스트 환경에서 실행해 보내왔는지, 복원할 수 있는 인스턴스의 백업이 준비되어 있는 것을 강력히 권장합니다.

u = User.find_by_username('<username>')
p = Project.find_by_full_path('<namespace/project>')
m = p.merge_requests.find_by(iid: <iid>)
MergeRequests::RebaseService.new(project: m.target_project, current_user: u).execute(m)

올바르지 않은 병합 요청 상태 수정

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

병합 요청의 변경이 병합된 후에도 열린(Open) 상태로 유지된다면, 레일스 콘솔에 액세스할 수 있는 사용자는 병합 요청의 상태를 수정할 수 있습니다. <username>, <namespace/project>, <iid>를 적절한 값으로 대체하세요:

경고: 데이터를 직접 변경하는 모든 명령에는 올바르게 실행되지 않거나 적절한 조건에서 실행되지 않을 경우에는 피해를 줄 수 있습니다. 테스트 환경에서 실행해 보내왔는지, 복원할 수 있는 인스턴스의 백업이 준비되어 있는 것을 강력히 권장합니다.

u = User.find_by_username('<username>')
p = Project.find_by_full_path('<namespace/project>')
m = p.merge_requests.find_by(iid: <iid>)
MergeRequests::PostMergeService.new(project: p, current_user: u).execute(m)

병합되지 않은 변경 사항을 가진 병합 요청에 대해 이 명령을 실행하면, 병합 요청이 merged into <branch-name>이라는 올바르지 않은 메시지를 표시합니다.

레일스 콘솔에서 병합 요청 닫기

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

병합 요청을 UI 또는 API를 통해 닫을 수 없는 경우, 레일스 콘솔 세션에서 병합 요청을 닫으려고 할 수 있습니다:

경고: 데이터를 변경하는 명령은 올바르게 실행되지 않거나 적절한 조건에서 실행되지 않을 경우에는 피해를 줄 수 있습니다. 명령을 항상 먼저 테스트 환경에서 실행하고 백업 인스턴스를 복원할 수 있는 상태로 유지하세요.

u = User.find_by_username('<username>')
p = Project.find_by_full_path('<namespace/project>')
m = p.merge_requests.find_by(iid: <iid>)
MergeRequests::CloseService.new(project: p, current_user: u).execute(m)

레일스 콘솔에서 병합 요청 삭제

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

병합 요청을 UI 또는 API를 통해 삭제할 수 없는 경우, 레일스 콘솔 세션에서 삭제를 시도할 수 있습니다:

경고: 데이터를 직접 변경하는 모든 명령에는 올바르게 실행되지 않거나 적절한 조건에서 실행되지 않을 경우에는 피해를 줄 수 있습니다. 테스트 환경에서 실행해 보내왔는지, 복원할 수 있는 인스턴스의 백업이 준비되어 있는 것을 강력히 권장합니다.

u = User.find_by_username('<username>')
p = Project.find_by_full_path('<namespace/project>')
m = p.merge_requests.find_by(iid: <iid>)
Issuable::DestroyService.new(container: m.project, current_user: u).execute(m)

병합 요청 pre-receive 후크 실패

병합 요청이 시간 초과되면 Puma 워커 시간이 초과되었음을 나타내는 메시지가 표시될 수 있습니다:

  • GitLab UI에서:

    병합 pre-receive 후크 중에 문제가 발생했습니다.
    500 Internal Server Error. 다시 시도하세요.
    
  • gitlab-rails/api_json.log 로그 파일에서:

    Rack::Timeout::RequestTimeoutException
    요청이 60000ms보다 오래 실행됨
    

이 오류는 병합 요청이 다음과 같은 경우에 발생할 수 있습니다:

  • 다양한 차이가 있는 경우
  • 대상 브랜치보다 많은 커밋이 있는 경우
  • 잠긴 Git LFS 파일에 대한 참조가 있는 경우

자체 관리 설치의 사용자는 서버 로그를 관리자 검토하여 오류의 원인을 확인할 수 있습니다. GitLab SaaS 사용자는 도움이 필요하실 경우 지원팀에 연락해 주세요.

캐시된 병합 요청 카운트

그룹에서 사이드바에 열린 병합 요청의 총 수가 표시됩니다. 값이 1000보다 크면 이 값은 캐시됩니다. 캐시된 값은 천 단위(또는 백만)로 반올림되며 24시간마다 업데이트됩니다.

head ref를 통해 로컬로 병합 요청 확인

병합 요청에는 리포지토리의 모든 이력과 병합 요청과 관련된 브랜치에 추가된 추가 커밋이 포함됩니다. 여기에는 병합 요청을 로컬에서 확인하는 몇 가지 방법이 나와 있습니다.

소스 프로젝트가 대상 프로젝트의 포크(비공개 포크도 포함)인 경우에도 병합 요청을 로컬에서 확인할 수 있습니다.

이는 각 병합 요청에 대해 사용할 수 있는 병합 요청 head ref (refs/merge-requests/:iid/head)에 의존합니다. 이를 사용하면 브랜치 대신 ID를 사용하여 병합 요청을 로컬에서 확인할 수 있습니다.

GitLab 16.6 이상에서는 병합 요청 head ref가 닫힌 후 14일이 지난 후 삭제됩니다. 그러면 더 이상 병합 요청이 로컬에서 head ref를 사용하여 확인할 수 없습니다. 병합 요청은 여전히 다시 열 수 있습니다. 병합 요청의 브랜치가 존재한다면 이는 영향을 받지 않으므로 확인할 수 있습니다.

glab을 사용하여 로컬에서 확인

glab mr checkout <merge_request_iid>

GitLab 터미널 클라이언트에서 자세한 내용을 확인하세요.

Git 별칭 추가하여 로컬에서 확인

다음 별칭을 ~/.gitconfig에 추가하세요:

[alias]
    mr = !sh -c 'git fetch $1 merge-requests/$2/head:mr-$1-$2 && git checkout mr-$1-$2' -

이제 어떤 저장소와 원격이든 특정 병합 요청을 확인할 수 있습니다. 예를 들어, GitLab에서 origin 원격의 ID 5인 병합 요청을 확인하려면:

git mr origin 5

이 명령은 로컬 mr-origin-5 브랜치로 병합 요청을 가져와 확인합니다.

.git/config를 수정하여 로컬에서 확인

.git/config 파일에서 GitLab 원격에 해당하는 섹션을 찾으세요. 다음과 같이 보입니다:

[remote "origin"]
  url = https://gitlab.com/gitlab-org/gitlab-foss.git
  fetch = +refs/heads/*:refs/remotes/origin/*

다음 명령으로 파일을 열 수 있습니다:

git config -e

이제 위의 섹션에 다음 줄을 추가하세요:

fetch = +refs/merge-requests/*/head:refs/remotes/origin/merge-requests/*

마지막으로, 다음과 같이 보이게 됩니다:

[remote "origin"]
  url = https://gitlab.com/gitlab-org/gitlab-foss.git
  fetch = +refs/heads/*:refs/remotes/origin/*
  fetch = +refs/merge-requests/*/head:refs/remotes/origin/merge-requests/*

이제 모든 병합 요청을 가져올 수 있습니다:

git fetch origin

...
From https://gitlab.com/gitlab-org/gitlab-foss.git
 * [new ref]         refs/merge-requests/1/head -> origin/merge-requests/1
 * [new ref]         refs/merge-requests/2/head -> origin/merge-requests/2
...

특정 병합 요청을 확인하려면:

git checkout origin/merge-requests/1

모든 작업은 git-mr 스크립트로 수행할 수 있습니다.

오류: 브랜치가 존재하는데 “source branch <branch_name> does not exist.” 오류가 발생하는 경우

이 오류는 GitLab 캐시가 Git 저장소의 실제 상태를 반영하지 않을 때 발생할 수 있습니다. 이는 Git 데이터 폴더가 noexec 플래그로 마운트된 경우에 발생할 수 있습니다.

선행 조건:

  • 관리자 권한이 있어야 합니다.

캐시를 강제로 업데이트하려면:

  1. 다음 명령으로 GitLab Rails 콘솔을 엽니다:

    sudo gitlab-rails console
    
  2. Rails 콘솔에서 다음 스크립트를 실행하세요:

    # 프로젝트 가져오기
    project = Project.find_by_full_path('affected/project/path')
    
    # 캐시에서 영향받는 브랜치가 있는지 확인 (false를 반환할 수 있음)
    project.repository.branch_names.include?('affected_branch_name')
    
    # 브랜치 캐시 만료
    project.repository.expire_branches_cache
    
    # 다시 영향받는 브랜치가 캐시에 있는지 확인 (이번에는 true를 반환해야 함)
    project.repository.branch_names.include?('affected_branch_name')
    
  3. 병합 요청을 다시로드하세요.