CI/CDをkatacodaで体験(初心者向け) - Part8(Being Picky With Git)


CI/CD入門

このぺーじでは、katacodaと呼ばれる「ブラウザから無料で勉強用のインスタンスを起動できるWebサービス」を利用してCI/CDを実践します
内容は上記リンクに沿うので、不明点があればそちらへどうぞ

Gitのバージョン管理について - Scenario 8 - Being Picky With Git

ここでは、CI/CDとして欠かせないGitによるバージョン管理について学習します
このシナリオで学習することをさっと確認する場合は概要を確認
理解に間違い等がございましたら、ぜひご指摘ください

概要

  • git cherry-pick <hash>で、特定のcommitを別のbranchのマージ
    • hashは複数指定可能
    • hashA..hashBのように連続して指定可能(hashAはマージに含みたいバージョンの一つ手前)
  • マージの際にconflictが発生した場合はgit mergeの際とほぼ同じ方法で解決可能
    1. git cherry-pick <hash>
    2. conflict発生
    3. git checkout --ours/theirs <file>
    4. git add
    5. git cherry-pick --continue(git commitは利用しない)

Step 1 - Cherry Picking

Gitを用いた開発では、master等から分岐したbranch上でcommitを繰り返し、統合する
git mergeでは、分岐後のcommitをすべて反映させるが、git cherry-pickは指定したcommitのみを反映させることが可能
このシナリオでは、new_branchの3世代前のバージョン、2世代前のバージョン、最新版をmasterに統合

$ git log --pretty=oneline --reverse new_branch
ESC[33m35bb08aa4d80d2214e7af28207af8e9312fd3250ESC[m Readme File
ESC[33m35182d3434fe6011c2a15c635e35bd61e5ff9c89ESC[m Initial commit, no items
ESC[33mfc5e301c9ccf0465599f3be8b71403e2be794b7aESC[m Initial list
ESC[33m2dc5608b8c88d38fd80235e1072da57d8b3c94ccESC[m Creating Second List
ESC[33m6aef159d692bb73f3f7860741d1877c44da58e59ESC[mESC[33m (ESC[mESC[1;32mnew_branchESC[mESC[33m)
$ git branch -va
* ESC[32mmaster    ESC[m 63b66b2 Empty list
  new_branchESC[m 6aef159 Adding final items to the list
$ git log --oneline
ESC[33m63b66b2ESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Empty list
ESC[33m35bb08aESC[m Readme File
$ git cherry-pick new_branch~3
[master 1e1c393] Initial commit, no items
 Date: Tue Oct 20 03:22:58 2020 +0000
 1 file changed, 2 insertions(+)
 create mode 100644 list.html
$ git log --oneline
ESC[33m1e1c393ESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Initial co
ESC[33m63b66b2ESC[m Empty list
ESC[33m35bb08aESC[m Readme File
$ git cherry-pick new_branch~2
[master 4b77632] Initial list
 Date: Tue Oct 20 03:22:59 2020 +0000
 1 file changed, 3 insertions(+)
$ git log --oneline
ESC[33m4b77632ESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Initial li
ESC[33m1e1c393ESC[m Initial commit, no items
ESC[33m63b66b2ESC[m Empty list
ESC[33m35bb08aESC[m Readme File
$ git cherry-pick new_branch
[master 981a34f] Adding final items to the list
 Date: Tue Oct 20 03:22:59 2020 +0000
 1 file changed, 1 insertion(+)
$ git log --oneline
ESC[33m981a34fESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Adding fin
ESC[33m4b77632ESC[m Initial list
ESC[33m1e1c393ESC[m Initial commit, no items
ESC[33m63b66b2ESC[m Empty list
ESC[33m35bb08aESC[m Readme File

また、git cherry-pickは以下のように一度に複数のcommitを処理することも可能

$ git cherry-pick new_branch~3 new_branch~2 new_branch
[master feaed88] Initial commit, no items
 Date: Tue Oct 20 03:36:35 2020 +0000
 1 file changed, 2 insertions(+)
 create mode 100644 list.html
[master 1d8352d] Initial list
 Date: Tue Oct 20 03:36:35 2020 +0000
 1 file changed, 3 insertions(+)
[master dce035e] Adding final items to the list
 Date: Tue Oct 20 03:36:35 2020 +0000
 1 file changed, 1 insertion(+)
$ git log --oneline
ESC[33mdce035eESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Adding fin
ESC[33m1d8352dESC[m Initial list
ESC[33mfeaed88ESC[m Initial commit, no items
ESC[33m5dae15aESC[m Empty list
ESC[33m89d91d5ESC[m Readme File

他にも連続するcommitを<commitA>..<commitB>のように指定することも可能

$ git cherry-pick new_branch~4..new_branch~2
[master f6e3642] Initial commit, no items
 Date: Tue Oct 20 03:45:21 2020 +0000
 1 file changed, 2 insertions(+)
 create mode 100644 list.html
[master 4b7a909] Initial list
 Date: Tue Oct 20 03:45:21 2020 +0000
 1 file changed, 3 insertions(+)
$ git cherry-pick new_branch
[master b71ad13] Adding final items to the list
 Date: Tue Oct 20 03:45:21 2020 +0000
 1 file changed, 1 insertion(+)
$ git log --oneline
ESC[33mb71ad13ESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Adding fin
ESC[33m4b7a909ESC[m Initial list
ESC[33mf6e3642ESC[m Initial commit, no items
ESC[33me44b269ESC[m Empty list
ESC[33me477a69ESC[m Readme File
(END)

Step 2 - Resolving Cherry Picking Conflict

step2,3では、git cherry-pickによるマージでコンフリクトが発生した場合の対処を説明

$ git cherry-pick new_branch~1
error: could not apply 65f1b54... Creating Second List
hint: after resolving the conflicts, mark the corrected paths  //conflictの発生
hint: with 'git add <paths>' or 'git rm <paths>'
hint: and commit the result with 'git commit'
$ git status
On branch master
You are currently cherry-picking commit 65f1b54.
  (fix conflicts and run "git cherry-pick --continue")
  (use "git cherry-pick --abort" to cancel the cherry-pick operation)

Unmerged paths:
  (use "git add <file>..." to mark resolution)

        both added:      list2.html   //git mergeの際と同様、conflict状態

no changes added to commit (use "git add" and/or "git commit -a")
$ git diff
ESC[1mdiff --cc list2.htmlESC[m
ESC[1mindex 4d4407a,ae60808..0000000ESC[m
ESC[1m--- a/list2.htmlESC[m
ESC[1m+++ b/list2.htmlESC[m
ESC[36m@@@ -1,3 -1,6 +1,10 @@@ESC[m
  <ul>ESC[m
ESC[32m++<<<<<<< HEADESC[m   //master上のlist2.html
ESC[32m +<li>Empty</li>ESC[m
ESC[32m++=======ESC[m   //new_branch上のlist2.html
ESC[32m+ <li>Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</li>ESC[m
ESC[32m+ <li>Aliquam tincidunt mauris eu risus.</li>ESC[m
ESC[32m+ <li>Vestibulum auctor dapibus neque.</li>ESC[m
ESC[32m+ <li>dapibus neque.</li>ESC[m
ESC[32m++>>>>>>> 65f1b54... Creating Second ListESC[m
  </ul>ESC[m
$ git checkout --theirs list2.html   //new_branch上のlist2.htmlの結果を優先

Step 3 - Continuing Cherry Picking After Conflict

step2にて、conflictの発生を確認、優先する変更を指定
ここでは、優先結果の反映されたcommitを実行
基本的には、git mergeの際と同じ手順だが、git commitの代わりにgit cherry-pick --continueを用いる

$ git log --oneline
ESC[33mb71ad13ESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Adding final item
ESC[33m4b7a909ESC[m Initial list
ESC[33mf6e3642ESC[m Initial commit, no items
ESC[33me44b269ESC[m Empty list
ESC[33me477a69ESC[m Readme File
$ ls -a
.  ..  .git  list2.html  list.html  README.md
$ cat list2.html
<ul>
<li>Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</li>
<li>Aliquam tincidunt mauris eu risus.</li>
<li>Vestibulum auctor dapibus neque.</li>
<li>dapibus neque.</li>
</ul>
$ git status
On branch master
You are currently cherry-picking commit 65f1b54.
  (fix conflicts and run "git cherry-pick --continue")
  (use "git cherry-pick --abort" to cancel the cherry-pick operation)

Unmerged paths:
  (use "git add <file>..." to mark resolution)

        both added:      list2.html

no changes added to commit (use "git add" and/or "git commit -a")
$ git add list2.html
$ git status
On branch master
You are currently cherry-picking commit 65f1b54.
  (all conflicts fixed: run "git cherry-pick --continue")
  (use "git cherry-pick --abort" to cancel the cherry-pick operation)

Changes to be committed:

        modified:   list2.html

$ git cherry-pick --continue   
[master aa8d155] Creating Second List cherry-pick
 Date: Tue Oct 20 03:45:21 2020 +0000
 1 file changed, 4 insertions(+), 1 deletion(-)
$ git log --oneline
ESC[33maa8d155ESC[mESC[33m (ESC[mESC[1;36mHEAD -> ESC[mESC[1;32mmasterESC[mESC[33m)ESC[m Creating Second L  
ESC[33mb71ad13ESC[m Adding final items to the list
ESC[33m4b7a909ESC[m Initial list
ESC[33mf6e3642ESC[m Initial commit, no items
ESC[33me44b269ESC[m Empty list
ESC[33me477a69ESC[m Readme File

ログの結果Creating Second Lからconflictが発生したcommitをmasterに反映できたことを確認