Git打補丁常見問題
往往覺得得到某個功能的補丁就覺得這個功能我就已經成功擁有了,可是在最后一步的打補丁的工作也是須要相當慎重的,甚至有可能還要比你獲取這個補丁花費的時間還要多。看到好多同行遇到這個問題,且近期自己也花費近20天「獲取,打,驗證」一個特性功能的補丁。趁熱總結一下,知識點可能不多,可是問題是相當棘手的。
$ git apply -h
usage: git apply [options] [<patch>...]
--exclude <path> don't apply changes matching the given path
--include <path> apply changes matching the given path
-p <num> remove <num> leading slashes from traditional diff paths
--no-add ignore additions made by the patch
--stat instead of applying the patch, output diffstat for the input
--numstat show number of added and deleted lines in decimal notation
--summary instead of applying the patch, output a summary for the input
--check instead of applying the patch, see if the patch is applicable
--index make sure the patch is applicable to the current index
--cached apply a patch without touching the working tree
--apply also apply the patch (use with --stat/--summary/--check)
-3, --3way attempt three-way merge if a patch does not apply
--build-fake-ancestor <file>
build a temporary index based on embedded index information
-z paths are separated with NUL character
-C <n> ensure at least <n> lines of context match
--whitespace <action>
detect new or modified lines that have whitespace errors
--ignore-space-change
ignore changes in whitespace when finding context
--ignore-whitespace ignore changes in whitespace when finding context
-R, --reverse apply the patch in reverse
--unidiff-zero don't expect at least one line of context
--reject leave the rejected hunks in corresponding *.rej files
--allow-overlap allow overlapping hunks
-v, --verbose be verbose
--inaccurate-eof tolerate incorrectly detected missing new-line at the end of file
--recount do not trust the line counts in the hunk headers
--directory <root> prepend <root> to all filenames
$
第一步檢測補丁有無問題
$ git apply --check xxx.patch
能檢測出現的問題有下面幾種樣例:
1. error: cannot apply binary patch to 'xxx' without full index line
xxx通常會是bin/png/gif等等二進制文件 詳細的原因就是patch中有指明要打上xxx文件,可是這個文件並不包括在這個patch中,不過有一個名字存在當中。遇到這個問題要重視。
2. error: core/java/android/provider/Settings.java: patch does not apply
出現這樣的通常會是補丁沖突,這樣的通常是強制打上補丁(使用--reject)后依據產生的*.rej文件來手動解決沖突。
3. warning: core/java/android/view/View.java has type 100644, expected 100755
出現這樣的警告通常是文件內沒有沖突,可是文件的權限發生變動。一般沒有影響。
第二步強制打補丁
$ git apply --reject xxx.patch
運行了這一步后會產生什么樣的結果,我對第一步的沖突來相應說明。
1.這樣的問題通常是制作補丁的開發者沒有將二進制文件制作到patch中雲,對於這樣的情況不會有不論什么的提示,由於patch中源資源文件都沒有,Git也沒有什么招術來解決。最好的方法是聯系補丁提供者。
2.這樣的情況是因為git apply是對照補丁中前后幾行代碼,假設沒有出如今目標文件里,那么這就是沖突。這個是比較常常出現的,對於這樣的情況會生成*.rej文件,能夠find ./ -name *.rej找到這些沖突的補丁,手動打上就好。
3.能夠考慮忽略。
眼下就這些,遇到新的問題再補充。
git am -3 -k后假設有沖突,不要運行git checkout。假設不願意改動沖突文件,佯裝改動一下,加入進去才干進行下一步。
git --git-dir=../other_proj_dir/.git format-patch -k -1 --stdout xxxxxxxxxxxxxxxxxx | git am -3 -k
git am相同有--reject選項,加入這個選項能夠將能打上的補丁先打上,沖突的文件生成*.rej文件。