Hatena::ブログ(Diary)

kanonjiの日記 RSSフィード

http://kanonji.info/blog/ 2013年2月頃に移転しました。

2011-02-22

普通のpatchコマンドで取り込めるdiffファイルをgitで作成する

まとめ

$ git diff --no-prefix HEAD~ > thisis.patch
$ patch --dry-run -p0 < thisis.patch
$ patch -p0 < thisis.patch

git diff--no-prefixをつける事で、普通のpatchで当てられるパッチファイルを出力できます。この例ではHEADの1個前*1からHEAD*2までのパッチです。

普通のpatchコマンドのほうの知識があまり無くて-p0がいまいちよく分からないんですが、git diff --no-prefixで作成したパッチファイルを当てるには必要みたいです。--dry-runは、実際には当てないけど当てた場合の結果を出力します。なので、まずは--dry-runで確認して、問題が無ければ実際にパッチを当てます。

エントリー書いた後に教えてもらった補足

patch -p1の様に-p0-p1にすれば、--no-prefixは付けなくても良いみたいです。patchコマンドに不慣れだったので言われるまで気がつかなかったんですが、言われてみればその通りでした。--no-prefixがdiff内にあるファイルパスに、1階層分のプレフィックスを付けるもので、-p1はそのファイルパスから1階層無視するものなので、そのまんまですね。@nojimageさんありがとうございました。

解説

gitにはgit format-patchというコマンドがあります。流石分散バージョン管理といった所か、git format-patchはパッチを直ぐにメール出来るようにmbox形式でパッチを生成してくれる*3らしい。そのパッチは、git send-emailgit imap-sendでメールできるようになっています。

ただ、普通のpatchコマンドでパッチを当てたい時には、mbox形式はむしろ困ったフォーマットです。一応、メールするのではなく*4パッチを当てるgit amというコマンドがあります。ただ、これが使えるのはgitで管理されてるプロジェクトだけ。

Subversionで管理してるプロジェクトに、gitで管理されてるプラグインを使うといったことがあり、プラグインの修正を取り込む必要が出てきました。本体はsvnなのでgit amは使えるはずも無く、なんとかpatchで当てられるdiffが必要でした。

-p0オプションについて

つまり、最初の "-p0" というオプションは「ディレクトリを無視しない」という意味になります。

パッチをあてる(その3:patchコマンドの-pオプションについて): 小粋空間

どうやらdiffの最初に記載されてるディレクトリパスの扱いのようです。なんとなくは分かったけど、まとめられるほど理解してないです。詳しくは上記サイトをどうぞ。

余談だけどGithubからパッチを得る方法

Githubに置いてるなら、URLにちょっと拡張子を追加するだけで、パッチファイルが保存できます。URLに.patch.diffをつける事で、それぞれgit format-patchgit diff相当で出力されます。

ただ、残念ながら.diffをつけても--no-prefixが無いgit diffなので、patchコマンド用にはなりません。

前述した追記の通り、patch -p1を使えば.diffを付けた方なら取り込めそうです。試してはないですけど。

https://github.com/kanonji/CakePHP-Search-plugin-sample/commit/89b74efba913ab4f08a25243915594b3f7600d2a

このコミットのURLに拡張子をつけます。

https://github.com/kanonji/CakePHP-Search-plugin-sample/commit/89b74efba913ab4f08a25243915594b3f7600d2a.patch

https://github.com/kanonji/CakePHP-Search-plugin-sample/commit/89b74efba913ab4f08a25243915594b3f7600d2a.diff

それぞれこんな出力です。

例2

https://github.com/kanonji/CakePHP-Search-plugin-sample/compare/ffc3bcaa427c85fb1aac...f410e481d1e190372443

Compare viewのURLに対しても出来ます。

https://github.com/kanonji/CakePHP-Search-plugin-sample/compare/ffc3bcaa427c85fb1aac...f410e481d1e190372443.patch

https://github.com/kanonji/CakePHP-Search-plugin-sample/compare/ffc3bcaa427c85fb1aac...f410e481d1e190372443.diff

試してないけどGithubでコミットやブランチやタグ間のdiffを見る、Compare viewを使う - kanonjiの日記に書いたタグやブランチの比較にも出来るんじゃないかな。でも、あんまりコミット数が多いCompare viewでやると、重たそうですが。

環境

MacMac OS X 10.5.8(Leopard)
git1.7.3.5

*1:HEAD~

*2:例では省略

*3:使ったこと無いのでよく分からないけど

*4:もしくはメールされてきた

anonymousanonymous 2015/07/03 13:01 > --no-prefixがdiff内にあるファイルパスに、1階層分のプレフィックスを付けるもので、-p1はそのファイルパスから1階層無視するものなので、そのまんまですね。@nojimageさんありがとうございました。

とありますが、 --no-prefix オプションを付けると git diff の出力に1階層分のプレフィックスを付け"ない"ので、
正しくは「--no-prefixオプションをつけない diff コマンドが出力結果内にあるファイルパスに、1階層分のプレフィックスを付けるもの」じゃないですかね?

スパム対策のためのダミーです。もし見えても何も入力しないでください
ゲスト


画像認証