我需要在两次提交之间运行git diff,结果应该是用相应的SHA引入的文件。
目前我可以这样做:
git diff --name-only [start-sha] [end-sha]
给出:
myfolder/a.txt
code/snippet.c
test.txt
但是如何在修改/添加每个文件时获取SHA,以便得到结果:
myfolder/a.txt 2314d344
code/snippet.c gfhr76kl
test.txt jk5534bf
图我可以这样做:
$files = git diff --name-only [start-sha] [end-sha]
foreach ($f in $files) {
$sha = git log -n1 --format=format:%H $f
print $f $sha
}
所以获取文件$ f被修改的最后一次提交/ SHA。
答案 0 :(得分:1)
不确定是否有内部git命令来执行此操作,但您可以随时循环访问文件并获取第一次提交:
{{1}}
答案 1 :(得分:1)
你的问题掩盖了一个根本问题。我们来看一个典型的提交图片段:
...--E--F--G--H--I--J <-- master
您选择了两个提交,例如E
和I
,然后运行git diff --name-only
(或git diff --name-status
)进行比较:
$ git diff --name-only <hash-E> <hash-I> myfolder/a.txt code/snippet.c test.txt
然后说:
...结果应该是使用 对应的SHA。
引入的文件
这些文件名出来意味着提交E
和/或I
中存在所有三个文件,但如果您在工作树中提交了E
,想要修改它以获得提交I
,这三个文件需要进行某种更改:创建,修改甚至删除。使用--name-status
也会为您提供种更改:A
用于&#34;文件将是新创建的&#34;,M
&#34;文件将被修改&#34;和D
for&#34;文件将被删除&#34;。 (当然,E
和I
中可能存在数十个或数千个相同的文件,因此不会在此处打印。)
但是现在你要求引入此更改的 对应的哈希值。可能没有 哈希。可能有多个。 (当然必须至少一个)。例如,test.txt
可能会在F
中被错误地删除(而不是被纠正),在H
中放回完整但错误,然后在I
中更正。同时,code/snippet.c
和 G
中可能会修改I
。
您希望为每个文件提供哪些提交哈希值? 的答案决定了如何找到它们。 (当然,如果只有一个这样的哈希,问题就会消失。)
xxfelixxx's answer给出一个(轻微的错误,但很容易修复和改进)方法来获得一个提交 - 第一个git log
打印。要修复一个错误并稍微改进一下,请将do
序列替换为:
do echo -n "$file "; git rev-list <starthash>..<endhash> -- "$file" | head -1
也就是说,我们希望在仅在指定的开始/停止点和上运行时查找由git rev-list
打印的提交哈希之一,以查找对该文件的更改。我们需要<starthash>..<endhash>
来执行初始提交限制,而-- $file
只需要选择添加,修改或删除该路径的提交。请注意,如果文件名中有空格,则需要引用它(所以我这样做),尽管读取git diff
的输出本身也很棘手。
使用head -1
可以获取触及该文件的最新提交,例如,我们的示例中code/snippet.c
和{{1} G
你获得了提交I
的哈希值。这是因为Git向后工作,从较新的提交到较旧的提交。如果您想要第一个,请使用I
,如果您想要所有这些,则需要更高级的格式。 : - )
(tail -1
和git log
之间存在另一个微妙的区别,涉及合并提交,但这可能不会对您产生影响。)