guyonがconfigsを修正する時、git branchをちゃんと理解したい!
始めに
「最後に」を見て頂けたらと思います。
開始
guyonは迷っていた。gitを使い始めてconfigsをデプロイできるようになったはいいが、Rakefileのrep_cloneタスクがイケていない事に気付いた。*1
このままでは、オフラインでconfigsの巻き戻しができない。
果たして今の自分の技術でちゃんと完了させることが出来るだろうか?
この機能追加をやるべきか、このままにするか・・・。
- 神は言った「stashとbranchの利用で済まないか?」。guyon:「stash??branch??」
- guyonはこの修正が失敗に終わった時のことを考えて、リポジトリのバックアップをとっておく事にした。「いつでも俺は戻れるんだ」と。
- guyonはbranchとstashを理解できていないが、とりあえず、アリスさんが辿った手順を参考にしやってみることにした。「習うより、慣れろだぜ」
[guyon ~/configs]$ git branch challenge #ブランチchallengeを作成 [guyon ~/configs]$ git branch #ブランチの一覧を確認 challenge * master
- ブランチの一覧を確認すると、今作成した「challenge」と、「master」が確認できる。
- ブランチ「master」はunfuddleのヘルプで言われるがままに作ったブランチ。gitのデフォルトのブランチはmasterを作るのだ。
- ブランチ名の先頭に「*」マークが付いているので、現在作業中のブランチはmasterということになる。
[guyon ~/configs]$ git checkout challenge Switched to branch "challenge" [guyon ~/configs]$ git branch * challenge master
- ブランチの一覧を確認すると、ブランチは「challnege」に変更された
- ブランチを変更する時はcheckoutで行うことができるようだ。
challengeブランチでRakefileの修正
- ブランチが切り替わった事を確認して、guyonはコードの修正を始めた。
[guyon ~/configs]$ git diff
- git cloneしているコードなんてもう必要ない。
- gitのdiffコマンドを激しく叩いた。
diff --git a/Rakefile.rb b/Rakefile.rb index f3e6cac..1d920ea 100644 --- a/Rakefile.rb +++ b/Rakefile.rb @@ -16,8 +16,6 @@ end # タスクの関連付け task :default => ["update"] -task :rep_build => ["rep_clone","update","work_dir_remove"] -task :rep_update => ["rep_clone","update"] desc "カレントディレクトリのConfigsからHOMEディレクトリにBuildする" task "update" => "win_rename_before"do @@ -40,15 +38,6 @@ task "update" => "win_rename_before"do p "Update Finish." end -desc "最新バージョンのconfigsリポジトリを作成する" -task "rep_clone" do - work_dir = HOME + "/configs_work/" + NOW - mkdir_p work_dir - cd work_dir - sh "git clone #{GIT_REPO}" - cd "./configs" -end - desc "workディレクトリを削除する" task "work_dir_remove" do remove_dir = HOME + "/configs_work/"
- これで良し、コミット。
[guyon ~/configs]$ git commit -a -m "rep_cloneタスクを削除" Created commit 1aa0ce9: rep_cloneタスクを削除 1 files changed, 0 insertions(+), 11 deletions(-)
ブランチを切り替えてみる
- guyonは、challengeブランチでの作業が一段落したので、masterブランチに切り替えてみた。
[guyon ~/configs]$ git checkout master Switched to branch "master"
- すると、Rakefile.rbの内容が、以前の状態に戻ってしまった・・・
- guyonは一瞬焦ったが、もう一度challengeブランチに切り替えてみると、さっき書いたコードが復元された!
[guyon ~/configs]$ git checkout challenge Switched to branch "challenge"
- つまりgitに管理されたディレクトリにおいては、Rakefile.rbというファイルは、編集作業をするための一時的なコピーでしかないのだ。
- gitがコミット時点のスナップショットを脈々と保存している.gitフォルダの履歴が全てであり、
- 今やその履歴は、masterと、そこから分岐するchallengeという二つの系統に分かれているのだ。
- guyonは写経しているにもかかわらず、コミット前にブランチを切り替えてmasterのRakefile.rbもmodefiedされた経験をした。
- 応用はまずは基本をやり終えてからだ。
- コミット・マージが基点になる事を知った。
※ここから少し独自路線へ・・・
vimrcの修正と巻き戻し
- なにを思ったかguyonはvimrcと.vimの整理をし始めた*2。それも膨大な量をだ。しかも既に何度かrakeコマンドを使ってデプロイをしている。
- guyonはvimの挙動がおかしい事に気付いた。このままではvimが使えない。コードが書けない。大変だ。
- ここでgit stashを利用するんだ。
[guyon ~/configs]$ git stash save Saved working directory and index state "WIP on challenge: 1aa0ce9... rep_cloneタスクを削除" HEAD is now at 1aa0ce9 rep_cloneタスクを削除
- よし、これで今の状態は保存できた。
- masterブランチへ戻してrakeでデプロイしたらまたchallegeブランチに戻ってきて作業の続きをするぞ。
[guyon ~/configs]$ git checkout master [guyon ~/configs]$ rake (in /Users/guyon/configs) copy rewrite /Users/guyon/configs/.vimrc => /Users/guyon/.vimrc copy rewrite /Users/guyon/configs/.vim/doc/tags => /Users/guyon/.vim/doc/tags "Update Finish." [guyon ~/configs]$ git checkout challenge Switched to branch "challenge"
- よしよし、さっき触っていた.vimrcの続きを編集するぞと意気込み、vimrcを開いたらmasterの状態になってしまっている。
- こっこれは。checkoutによってbranchを切り替えた事によって修正が全部消えたのか!?
- そ、そうだ。俺はこの為にstash saveをしているんだ。状態を元に戻せるはず。
[guyon ~/configs]$ git stash pop
- guyonはchallengeで編集してた状態に戻す事に成功した。
- これで、rep_cloneタスクが無くなってもなんの問題もないな。
- ブランチのmergeに関しては次の機会にチャレンジするぜ。
- mergeの機会は近い将来あるだろう。
最後に
- id:zariganitoshさんの記事を元ネタにして半写経させて頂きました。非常にわかりやすい例題のエントリーの掲載に感謝です。
- もしパロディ(内容も)がまずかったら修正・削除させて頂きます。その場合はコメントなどでお知らせ頂けたら幸いです。
あわせて読みたい。(元ネタエントリー)
アリスがチャレンジなコードを書く時、git branchをちゃんと理解したい! - ザリガニが見ていた...。
http://d.hatena.ne.jp/zariganitosh/20080912/1221260782
まとめ
- git使うならbranch活用すべし
- まだbranchの利用について理解できていないので、もっと学ぶ。
- コミットをすることでスナップショットができる。
- stashは作業状態を保管できる。
- popを使ったがapplyとclear併用でも可能。