Git,  Programming

[Git] 특정 Commit 가져오기 (Cherry-Pick)

Git을 사용하다보면 실수로 다른 branch에 잘못된 commit을 수행하거나 하는 경우에 다른 branch의 commit을 가져와야 하는 경우가 종종 발생한다. 이 때 사용할 수 있는 명령어가 cherry-pick이다.

git cherry-pick 명령어는 특정 commit을 현재 HEAD가 가리키는 branch에 추가할 수 있게 한다. 참고로 cherry-pick을 하게되면 기존 commit을 삭제하며 옮기는 (move)가 아니라 복사 (copy)하는 것이다.

저장소 이력
$ git cherry-pick [commit hash number]

사용법은 원하는 branch로 이동하여 commit hash number를 입력하면 된다.

Example 1

만약 위 git graph와 같이 main branch와 b1 branch가 있을 때, b1의 “Implement sub function”을 cherry-pick 한다고 했을 때, 다음과 같이 수행하면 된다.

$ git checkout b1
$ git log --oneline
e98d075 Add mul.cpp
99b2114 Implement sub function
52e3172 Initial release

우리가 cherry-pick 하고자 하는 hash number는 99b2114이다.

$ git checkout main
$ git cherry-pick 99b2114
[main 6baba8b] Implement sub function
 1 file changed, 4 insertions(+)
 create mode 100644 src/sub.cpp

그리고 git graph를 보면 commit이 새롭게 추가가 된 것을 볼 수 있다.

Example 2: Conflict Case

Cherry-pick을 진행 할 때, conflict가 발생되는 경우도 있다. 그런 경우 두 가지 옵션이 존재한다.

Conflict 해결하고 cherry-pick 진행

만약 위와 같은 git graph status를 가지는 경우에 특정 commit을 cherry-pick을 하게되면 main branch와 b1 branch가 conflict가 발생될 것이라 가정하자.

$ git cherry-pick 1fa7764
error: could not apply 1fa7764... Update README.md
hint: after resolving the conflicts, mark the corrected paths
hint: with 'git add <paths>' or 'git rm <paths>'
hint: and commit the result with 'git commit'

이 때 git conflict를 해결하고 다음 명령어를 수행하게 되면 정상적으로 cherry-pick이 된다.

# Resolve conflict
$ git add . # Staging the file
$ git cherry-pick --continue

Update README.md

Conflicts:
    README.md
#
# It looks like you may be committing a cherry-pick.
# If this is not correct, please remove the file
#   .git/CHERRY_PICK_HEAD
# and try again.


# Please enter the commit message for your changes. Lines starting
# with '#' will be ignored, and an empty message aborts the commit. 
# On branch main
# Your branch is ahead of 'origin/main' by 1 commit. 
#   (use "git push" to publish your local commits)
#
# You are currently cherry-picking.
#   (all conflicts fixed: run "git commit")
#
# Changes to be committed:
#
#   modified:   README.md
#
[main 6053052] Update README.md
 1 file changed, 1 insertion(+), 1 deletion(-)

참고로 다음과 같은 방식으로 수행하게 되면 새롭게 commit log를 작성하여 cherry-pick 할 수도 있다.

# # Resolve conflict
$ git add . # Staging the file
$ git commit -m "commit log"

Cherry-pick 중단

Conflict가 발생하는 경우 cherry-pick을 중단하고 이전 상태로 돌아가기 위해선 다음 옵션으로 명령어를 수행하면 된다.

$ git cherry-pick 1fa7764
error: could not apply 1fa7764... Update README.md
hint: after resolving the conflicts, mark the corrected paths
hint: with 'git add <paths>' or 'git rm <paths>'
hint: and commit the result with 'git commit'
$ git cherry-pick --abort

Reference

  1. https://backlog.com/git-tutorial/kr/stepup/stepup7_4.html

Leave a Reply

Your email address will not be published. Required fields are marked *