Git 리베이스: 알아야 할 모든 것
게시 됨: 2022-12-15 Git rebase
명령은 두 개의 소스 코드 분기를 하나로 결합합니다. Git merge
명령도 마찬가지입니다. rebase
가 무엇을 하는지, 어떻게 사용하는지, merge
을 대신 사용하는 경우에 대해 설명합니다.
힘내 폭발
힘내 병합이란 무엇입니까?
힘내 리베이스 란 무엇입니까?
다른 지점으로 리베이스하는 방법
Git 리베이스 대 병합: 어느 것을 사용해야 합니까?
리베이스하거나 리베이스하지 않습니까?
힘내 폭발
다른 버전 제어 시스템과 느린 업데이트 및 커밋에 좌절한 Linux 커널로 유명한 Linus Torvalds는 2005년에 자신의 시스템을 작성하기 위해 한 달을 비워두었습니다. 그는 그것을 Git이라고 명명했습니다.
GitHub, GitLab 및 BitBucket과 같은 사이트는 Git을 공생적으로 홍보하고 혜택을 받았습니다. 오늘날 Git은 전 세계적으로 사용되며 2022년 설문 조사에서 응답자 71,000명 중 98%가 Git를 버전 제어 시스템으로 사용했습니다.
Git의 주요 설계 결정 중 하나는 속도였습니다. 특히 지점과의 작업은 최대한 빨라야 했습니다. 분기는 버전 제어 시스템의 기본 부분입니다. 프로젝트 리포지토리에는 기본 또는 마스터 분기가 있습니다. 이것은 프로젝트의 코드 베이스가 있는 곳입니다. 새로운 기능과 같은 개발은 분리된 사이드 브랜치에서 이루어집니다. 이렇게 하면 분기에서 수행된 작업이 마스터 분기를 엉망으로 만드는 것을 중지하고 코드 기반의 다른 부분에서 동시 개발이 발생할 수 있습니다.
사이드 브랜치의 개발이 완료되면 개발 브랜치를 마스터 브랜치로 병합하여 변경 사항을 마스터 브랜치로 이전합니다. 다른 버전 제어 시스템에서 브랜치로 작업하는 것은 어렵고 계산 비용이 많이 듭니다. Git에서 브랜치 작업은 매우 빠르고 매우 가볍습니다. 한때 지루하고 다른 시스템에서는 자주 피했던 작업이 Git에서는 사소해졌습니다.
Git rebase
명령은 한 분기에서 다른 분기로 변경 사항을 전송하는 또 다른 방법입니다. merge
및 rebase
명령은 목적이 비슷하지만 서로 다른 방식으로 목적을 달성하고 결과가 약간 다릅니다.
힘내 병합이란 무엇입니까?
그렇다면 Git merge
명령은 무엇입니까? 새 기능을 작업하기 위해 dev-branch
라는 브랜치를 만들었다고 가정해 보겠습니다.
몇 가지 커밋을 하고 새 기능을 테스트합니다. 모두 잘 작동합니다. 이제 새 기능을 master
브랜치로 보내려고 합니다. 다른 브랜치를 병합하려면 master
브랜치에 있어야 합니다.
병합하기 전에 명시적으로 확인하여 master
분기에 있는지 확인할 수 있습니다.
자식 체크 아웃 마스터
이제 Git에게 dev-branch
를 master
브랜치인 현재 브랜치로 병합하도록 지시할 수 있습니다.
자식 병합 개발 지점
merge
이 완료되었습니다. master
브랜치를 체크 아웃하고 컴파일하면 새로 개발된 기능이 포함됩니다. Git이 실제로 수행한 것은 3방향 병합입니다. master
및 dev-branch
브랜치의 가장 최근 커밋과 dev-branch
가 생성되기 직전 master
브랜치의 커밋을 비교합니다. 그런 다음 master
브랜치에서 커밋을 수행합니다.
병합은 아무 것도 삭제하지 않고 Git 기록을 변경하지 않기 때문에 비파괴적인 것으로 간주됩니다. dev-branch
는 여전히 존재하며 이전 커밋은 변경되지 않습니다. 3방향 병합 결과를 캡처하는 새 커밋이 생성됩니다.
병합 후 Git 리포지토리는 대체 줄이 분기된 후 기본 타임라인으로 돌아가는 타임라인처럼 보입니다.
dev-branch
분기가 master
분기에 통합되었습니다.
한 프로젝트에 많은 분기가 있는 경우 프로젝트 히스토리가 혼란스러울 수 있습니다. 이는 프로젝트에 기여자가 많은 경우에 자주 발생합니다. 개발 노력이 다양한 경로로 분할되기 때문에 개발 이력은 비선형적입니다. 브랜치에 자체 브랜치가 있으면 커밋 히스토리를 푸는 것이 훨씬 더 어려워집니다.
master
브랜치에 커밋되지 않은 변경 사항이 있는 경우 병합하기 전에 이러한 변경 사항에 대해 작업을 수행해야 합니다. 새 분기를 만들고 거기에서 변경 사항을 커밋한 다음 병합을 수행할 수 있습니다. 그런 다음 임시 분기를 다시 마스터 분기로 병합해야 합니다.
그것은 작동하지만 Git에는 새 분기를 만들지 않고도 동일한 작업을 수행하는 명령이 있습니다. stash
명령은 커밋되지 않은 변경 사항을 저장하고 stash pop
으로 다시 호출할 수 있도록 합니다.
다음과 같이 사용합니다.
숨기는 장소 자식 병합 개발 지점 숨김 팝
최종 결과는 저장되지 않은 변경 사항이 복원된 병합된 분기입니다.
힘내 리베이스 란 무엇입니까?
Git rebase
명령은 완전히 다른 방식으로 목표를 달성합니다. 리베이스하려는 브랜치에서 모든 커밋을 가져와서 리베이스하려는 브랜치의 끝에서 재생합니다.
이전 예를 들어 어떤 작업을 수행하기 전에 Git 리포지토리는 다음과 같습니다. dev-branch
라는 브랜치가 있고 이러한 변경 사항을 master
브랜치로 옮기고 싶습니다.
rebase
후에는 하나의 완전히 선형적인 변경 타임라인처럼 보입니다.
dev-branch
가 제거되었고 dev-branch
-branch의 커밋이 master 브랜치에 추가되었습니다. 최종 결과는 처음에 dev-branch
의 커밋이 실제로 master
브랜치에 직접 커밋된 것과 동일합니다. 커밋은 master
브랜치에 고정되는 것이 아니라 "재생"되고 새로 추가됩니다.
이것이 rebase
명령이 파괴적인 것으로 간주되는 이유입니다. 리베이스된 브랜치는 더 이상 별도의 브랜치로 존재하지 않으며 프로젝트의 Git 기록이 다시 작성되었습니다. 어떤 커밋이 원래 dev-branch
에 만들어졌는지 나중에 확인할 수 없습니다.
그러나 단순하고 선형적인 역사를 남깁니다. 수십 또는 수백 개의 분기 및 병합이 있는 리포지토리와 비교하여 Git 로그를 읽거나 그래픽 git GUI를 사용하여 리포지토리의 그래프를 보는 것과 비교하면 리베이스된 리포지토리는 이해하기 쉽습니다.
다른 지점으로 리베이스하는 방법
git rebase
예제를 사용해 봅시다. new-feature
라는 분기가 있는 프로젝트가 있습니다. 이와 같이 해당 분기를 master
분기로 rebase
합니다.
먼저 master
브랜치에 눈에 띄는 변경 사항이 없는지 확인합니다.
자식 상태
new-feature
분기를 확인합니다.
git checkout 새로운 기능
우리는 Git에게 현재 브랜치를 마스터 브랜치로 rebase
하도록 지시합니다.
자식 리베이스 마스터
우리는 여전히 두 개의 분기가 있음을 알 수 있습니다.
자식 분기
master
브랜치로 다시 교체합니다.
자식 체크 아웃 마스터
새 기능 분기를 현재 분기로 병합합니다. 이 경우에는 master
분기입니다.
자식 병합 새로운 기능
흥미롭게도 최종 병합 후에도 여전히 두 개의 분기가 있습니다.
차이점은 이제 new-feature
브랜치의 헤드와 master
브랜치의 헤드가 동일한 커밋을 가리키도록 설정되었으며 Git 기록에는 별도의 new-feature
브랜치가 있었다는 것이 표시되지 않습니다. 지점 레이블.
Git 리베이스 대 병합: 어느 것을 사용해야 합니까?
rebase
대 merge
의 경우가 아닙니다. 둘 다 강력한 명령이며 아마 둘 다 사용할 것입니다. 즉, rebase
가 제대로 작동하지 않는 사용 사례가 있습니다. merge
을 사용하여 실수로 인한 Unpicking 실수는 불쾌하지만 rebase
로 인한 unpicking 오류는 지옥입니다.
당신이 리포지토리를 사용하는 유일한 개발자라면 rebase
로 재앙적인 일을 할 가능성이 적습니다. 예를 들어 여전히 rebase
방향으로 리베이스하고 마스터 브랜치를 new-feature
브랜치로 rebase
할 수 있습니다. master
브랜치를 다시 가져오려면 이번에는 new-feature
브랜치에서 master
브랜치로 다시 rebase
해야 합니다. 이상하게 보이는 기록이 있지만 master
분기가 복원됩니다.
다른 사람이 작동할 가능성이 있는 공유 분기에서 rebase
를 사용하지 마십시오. 리베이스된 코드를 원격 저장소로 푸시할 때 저장소 변경으로 인해 많은 사람들에게 문제가 발생할 것입니다.
프로젝트에 기여자가 여러 명 있는 경우 안전한 방법은 공용 분기가 아닌 로컬 리포지토리에서만 rebase
를 사용하는 것입니다. 마찬가지로 풀 요청이 코드 검토의 일부를 구성하는 경우 rebase
를 사용하지 마십시오. 또는 적어도 풀 리퀘스트를 생성한 후 rebase
를 사용하지 마십시오. 다른 개발자가 커밋을 보고 있을 가능성이 높습니다. 즉, 변경 사항이 master
브랜치에 없더라도 퍼블릭 브랜치에 있음을 의미합니다.
위험은 이미 원격 리포지토리로 푸시된 커밋을 rebase
하고 다른 개발자가 해당 커밋에 대한 작업을 이미 수행했을 수 있다는 것입니다. 로컬 rebase
는 기존 커밋을 사라지게 합니다. 이러한 변경 사항을 저장소에 푸시하면 인기를 얻지 못할 것입니다.
다른 기여자들은 자신의 작업을 리포지토리로 다시 푸시하기 위해 지저분한 merge
을 거쳐야 합니다. 그런 다음 변경 사항을 로컬 리포지토리로 다시 가져오면 중복된 변경 사항을 선택 해제해야 합니다.
리베이스하거나 리베이스하지 않습니까?
Rebase
는 프로젝트에서 불법일 수 있습니다. 지역적, 문화적 반대가 있을 수 있습니다. 일부 프로젝트 또는 조직에서는 rebase
를 이단의 한 형태로 간주하고 모독 행위로 간주합니다. 어떤 사람들은 Git 기록이 발생한 일에 대한 불가침의 영구적인 기록이어야 한다고 생각합니다. 따라서 rebase
는 테이블에서 벗어날 수 있습니다.
그러나 개인 브랜치에서 로컬로 사용되는 rebase
는 유용한 도구입니다.
리베이스 한 후 푸시하고 유일한 개발자인 브랜치로 제한하십시오. 또는 적어도 모든 개발이 중단되고 다른 누구도 브랜치의 커밋에서 벗어나 다른 작업을 기반으로 하지 않는 경우입니다.
그렇게 하면 문제를 피할 수 있습니다.
관련: Git 버전 확인 및 업데이트 방법