有沒有什麼辦法讓git給你提交一個提交文件中的特定行的提交日誌?檢索文件中特定行的提交日誌?
像git blame
,但git blame
會告訴你觸摸特定線的最後提交。
我真的很想得到一個類似的日誌,而不是提交到文件中任何地方的提交列表,而只是觸及特定行的提交。
有沒有什麼辦法讓git給你提交一個提交文件中的特定行的提交日誌?檢索文件中特定行的提交日誌?
像git blame
,但git blame
會告訴你觸摸特定線的最後提交。
我真的很想得到一個類似的日誌,而不是提交到文件中任何地方的提交列表,而只是觸及特定行的提交。
參見Git: discover which commits ever touched a range of lines。
Since Git 1.8.4,git log
具有-L
可以觀看範圍內的行的演變。
例如,假設您查看git blame
的輸出。這裏-L 150,+11
手段「只能看線150至150 + 11」:
$ git blame -L 150,+11 -- git-web--browse.sh
a180055a git-web--browse.sh (Giuseppe Bilotta 2010-12-03 17:47:36 +0100 150) die "The browser $browser is not
a180055a git-web--browse.sh (Giuseppe Bilotta 2010-12-03 17:47:36 +0100 151) fi
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 152) fi
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 153)
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 154) case "$browser" in
81f42f11 git-web--browse.sh (Giuseppe Bilotta 2010-12-03 17:47:38 +0100 155) firefox|iceweasel|seamonkey|iceape)
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 156) # Check version because firefox < 2.0 do
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 157) vers=$(expr "$($browser_path -version)"
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 158) NEWTAB='-new-tab'
5d6491c7 git-browse-help.sh (Christian Couder 2007-12-02 06:07:55 +0100 159) test "$vers" -lt 2 && NEWTAB=''
a0685a4f git-web--browse.sh (Dmitry Potapov 2008-02-09 23:22:22 -0800 160) "$browser_path" $NEWTAB "[email protected]" &
而且你要知道現在是什麼線155
然後歷史,使用git log
。在這裏,-L 155,155:git-web--browse.sh
的意思是「在名爲git-web--browse.sh
的文件中跟蹤155行到155行的演變」。
$ git log --pretty=short -u -L 155,155:git-web--browse.sh
commit 81f42f11496b9117273939c98d270af273c8a463
Author: Giuseppe Bilotta <[email protected]>
web--browse: support opera, seamonkey and elinks
diff --git a/git-web--browse.sh b/git-web--browse.sh
--- a/git-web--browse.sh
+++ b/git-web--browse.sh
@@ -143,1 +143,1 @@
-firefox|iceweasel)
+firefox|iceweasel|seamonkey|iceape)
commit a180055a47c6793eaaba6289f623cff32644215b
Author: Giuseppe Bilotta <[email protected]>
web--browse: coding style
diff --git a/git-web--browse.sh b/git-web--browse.sh
--- a/git-web--browse.sh
+++ b/git-web--browse.sh
@@ -142,1 +142,1 @@
- firefox|iceweasel)
+firefox|iceweasel)
commit 5884f1fe96b33d9666a78e660042b1e3e5f9f4d9
Author: Christian Couder <[email protected]>
Rename 'git-help--browse.sh' to 'git-web--browse.sh'.
diff --git a/git-web--browse.sh b/git-web--browse.sh
--- /dev/null
+++ b/git-web--browse.sh
@@ -0,0 +127,1 @@
+ firefox|iceweasel)
您可以使用pick-ax獲取一組提交。
git log -S'the line from your file' -- path/to/your/file.txt
這會給你所有影響該文件中文本的提交。如果文件在某個時候被重命名,則可以添加 - follow-parent。
如果你想在每一個編輯的視察提交,可以導致與git顯示管:
git log ... | xargs -n 1 git show
我不知道我怎麼看這個幫助。如果文字受到影響,則線條不再一樣,因此鎬只會向您顯示最近的變化。然後你必須做'git log'''''''這個行的前一個版本,等等,就像你最終用'git blame -L'做的一樣。而且它會比'git blame'慢,因爲它必須到處尋找文本,而不僅僅是在特定的地方。 – Cascabel
你可以在那裏使用正則表達式來使它更接受。目前沒有一些精心編寫的腳本,無法「及時導入補丁」。我希望gitk能夠在未來的補丁視圖中獲得此功能。 –
@Jefromi是對的,這個答案似乎是錯誤的 –
我不相信有內置的這樣的東西。這很棘手,因爲一條線很少會發生多次變化,而文件的其他部分也不會發生實質性變化,所以您最終會發現線數變化很大。
如果你夠幸運的話,該行總是有某些識別特徵,例如,對名稱從未改變的變量進行賦值,您可以使用git blame -L
的正則表達式選項。例如:
git blame -L '/variable_name *= */',+1
但這隻能找到第一匹配該正則表達式,所以如果你沒有匹配行的一個好辦法,這不是太大的幫助。
我想,你可以破解一些東西。我沒有時間寫出代碼,但是......沿着這些方向。運行git blame -n -L $n,$n $file
。第一個字段是先前提交的提交,第二個字段是中的行號,提交,因爲它可能已更改。抓住這些,並運行git blame -n $n,$n $commit^ $file
,即從上次更改文件之前的提交開始的相同事情。
(。請注意,這將讓你失望,如果最後一次提交的是改了行是一個合併提交的主要方式,如果該行修改的合併和解決衝突的一部分,這可能發生)
編輯:我今天從2011年3月發生了this mailing list post,其中提到tig
和git gui
有一個功能可以幫助您做到這一點。它看起來像git本身一直在考慮的功能,但沒有完成。
這將調用git blame
爲每有意義的修訂,以顯示文件$FILE
行$LINE
:
git log --format=format:%H $FILE | xargs -L 1 git blame $FILE -L $LINE,$LINE
像往常一樣,怪顯示每行開頭的版本號。你可以附加
| sort | uniq -c
得到聚集結果,就像改變這一行的提交列表。 (不完全是,如果代碼只是被移動了,這可能會顯示相同的提交ID兩次,以用於不同的內容,對於更詳細的分析,您必須對相鄰提交的git blame
結果進行滯後比較。 ?)
再次,我認爲這不起作用,因爲它不跟蹤該行的以前的位置。所以,如果一條線被添加了2次提交之前,你會看另一條線 –
這裏是定義一個git的別名的解決方案,這樣你就可以使用它這樣:
git rblame -M -n -L '/REGEX/,+1' FILE
輸出例如:
00000000 18 (Not Committed Yet 2013-08-19 13:04:52 +0000 728) fooREGEXbar
15227b97 18 (User1 2013-07-11 18:51:26 +0000 728) fooREGEX
1748695d 23 (User2 2013-03-19 21:09:09 +0000 741) REGEXbar
您可以定義別名您.gitconfig或簡單地運行下面的命令
git config alias.rblame !sh -c 'while line=$(git blame "[email protected]" $commit 2>/dev/null); do commit=${line:0:8}^; [ 00000000^ == $commit ] && commit=$(git rev-parse HEAD); echo $line; done' dumb_param
這是難看的一行,所以這裏是解模糊的等效bash函數:
git-rblame() {
local commit line
while line=$(git blame "[email protected]" $commit 2>/dev/null); do
commit="${line:0:8}^"
if [ "00000000^" == "$commit" ]; then
commit=$(git rev-parse HEAD)
fi
echo $line
done
}
的鎬溶液(git的日誌 - 鎬正則表達式-S'REGEX')只會給你添加/刪除行,而不是包含正則表達式的行的其他改動。
此解決方案的一個限制是,git blame僅返回第一個REGEX匹配項,因此如果存在多個匹配項,則遞歸可能會「跳轉」以跟隨另一行。一定要檢查完整的歷史記錄輸出以發現這些「跳躍」,然後修復REGEX以忽略寄生蟲線。
最後,這裏要說的是,在每次運行混帳顯示承諾得到充分的差異的替代版本:
git config alias.rblameshow !sh -c 'while line=$(git blame "[email protected]" $commit 2>/dev/null); do commit=${line:0:8}^; [ 00000000^ == $commit ] && commit=$(git rev-parse HEAD); git show $commit; done' dumb_param
一個非常簡單的方法是使用vim-fugitive。只要打開Vim的文件,選擇線(S)你有興趣使用V
,然後輸入
:Glog
現在你可以使用:cnext
和上看到該行被修改該文件的所有版本。在任何時候,輸入:Gblame
查看sha,作者和日期信息。
嘗試使用Git 1.8.4中實現的以下命令。
git log --pretty=short -u -L <upperLimit>,<lowerLimit>:<path_to_filename>
所以,你的情況upperLimit
& lowerLimit
是感動line_number
我認爲'--pretty = short'在使用'-L'時會被忽略。請改正 –
你可以混合git blame
和git log
命令檢索彙總的各git的怪命令承諾和追加他們。像下面的bash + awk腳本。它將提交摘要作爲代碼註釋內聯。
git blame FILE_NAME | awk -F" " \
'{
commit = substr($0, 0, 8);
if (!a[commit]) {
query = "git log --oneline -n 1 " commit " --";
(query | getline a[commit]);
}
print $0 " // " substr(a[commit], 9);
}'
在一個行:
git blame FILE_NAME | awk -F" " '{ commit = substr($0, 0, 8); if (!a[commit]) { query = "git log --oneline -n 1 " commit " --"; (query | getline a[commit]); } print $0 " // " substr(a[commit], 9); }'
在我行編號已經隨着時間的推移發生了很大變化。 我也在git 1.8.3上,它不支持「git blame -L」中的正則表達式。 (RHEL7仍具有1.8.3)
myfile=haproxy.cfg
git rev-list HEAD -- $myfile | while read i
do
git diff -U0 ${i}^ $i $myfile | sed "s/^/$i /"
done | grep "<sometext>"
Oneliner:
myfile=<myfile> ; git rev-list HEAD -- $myfile | while read i; do git diff -U0 ${i}^ $i $myfile | sed "s/^/$i /"; done | grep "<sometext>"
這當然可以製作成腳本或功能。
簡化@馬特的答案 -
git blame -L14,15 -- <file_path>
在這裏,你會得到一個怪對線條14 to 15
。
由於-L
選項預期Range
爲PARAM我們不能得到一個Blame
使用-L
option`一行。
參見:[Git的指責 - 前提交(http://stackoverflow.com/questions/5098256/git-blame-prior-commits) – joeytwiddle