tak*_*hin 5 git git-rebase git-reflog
在我做了交互式rebase之后:git rebase -i HEAD~20我得到了一个新的提交,例如ea1234ea
我知道历史记录在reflog中,但是如何获得此提交中压缩的提交列表,包括它们的标识符(sha)?
git show ea1234ea 将显示一个提交消息,其中列出了被压扁的消息,但没有标识符.
从...开始git reflog。输出将如下所示(但有更多rebase -i条目):
aa4e140 HEAD@{0}: rebase -i (finish): returning to refs/heads/branch\naa4e140 HEAD@{1}: rebase -i (squash): c1-c3, squashed\n3a422a7 HEAD@{2}: rebase -i (squash): # This is a combination of 2 commits.\nf7cac12 HEAD@{3}: rebase -i (start): checkout HEAD~3\n283263c HEAD@{4}: commit: blah yadda etc, but not a rebase\nRun Code Online (Sandbox Code Playgroud)\n\n最后一个非rebase行具有提交的 SHA1,该提交是您执行rebase -i. 此时,您可能想在其上粘贴临时分支或标签,尽管这在技术上不是必需的。在这里我将temp在其上放置一个轻量级标签,命名为:
git tag temp 283263c\nRun Code Online (Sandbox Code Playgroud)\n\n现在你可以简单地运行git log temp, 或(将其限制为您重新设置的基础):
git log temp --not HEAD\nRun Code Online (Sandbox Code Playgroud)\n\n或者:
\n\ngit log temp ^HEAD\nRun Code Online (Sandbox Code Playgroud)\n\n(这是拼写同一事物的两种方式)1,或:
\n\ngit log -n 20 temp\nRun Code Online (Sandbox Code Playgroud)\n\n(这使用了 rebased 中有 20 次提交的事实HEAD~20..HEAD,只有当原始历史是线性的时才是正确的,当然取决于该~20部分)。
完成临时标签后,将其删除:
\n\ngit tag -d temp\nRun Code Online (Sandbox Code Playgroud)\n\n其工作原理是,rebase -i实际上并不删除 任何提交,它只是添加 新的提交。(事实上,几乎每个 git 命令都是如此。垃圾收集过程除外,它会删除未引用的对象。)
完整的变基“提交和分支”参数(即忽略像-i和-p标志这样的重要内容)是:start-point、destination和branch-name。该文档巧妙地将前两个伪装为“upstream”和“onto”(说真的,“onto”不是一个坏名字,我将在下面坚持使用它,但“upstream”在某些情况下会产生误导)。start-point之后的所有提交,直到branch的顶端,都被复制(或省略或压缩或其他什么),本质上是通过一次一个地挑选它们,作为添加到生长在的分支上的新提交目的地。如果原始提交树看起来(部分)像这样:
old -- start-point -- c2 -- c3 -- c4 <-- branch\n \\\n onto -- c6 -- c7 <-- another-branch\nRun Code Online (Sandbox Code Playgroud)\n\n然后变基开始通过复制(或“重播更改”) (起点后的c2第一次提交)到相同的更改(但具有不同的提交信息) ,将其放置为其父级:c2\'onto
old -- start-point -- c2 -- c3 -- c4 <-- branch\n \\\n onto -- c6 -- c7 <-- another-branch\n \\\n c2\'\nRun Code Online (Sandbox Code Playgroud)\n\n然后它复制c3到一个新的 ( c3\') 版本,c3\'\ 的父版本是c2\',依此类推。当这一切完成后,它会将标签 ( branch) 从 上剥离c4,并将其粘贴到指向最后一个新提交 ( c4\') 上:
old -- start-point -- c2 -- c3 -- c4 <-- [no label]\n \\\n onto -- c6 -- c7 <-- another-branch\n \\\n c2\' -- c3\' -- c4\' <-- branch\nRun Code Online (Sandbox Code Playgroud)\n\n请注意,旧的提交(start-point、c2、c3和c4)仍然存在,只是不再具有分支标签。另请注意,在这种特殊情况下(使用--onto如图所示的参数和特定的提交树),名为自身的提交变得“不可见”(与throughstart-point含义相同),因为它不再有任何分支或标签指向它\xe2\x80\x94,当然,除非您在执行变基之前或之后设置了一个。(通常没有这样的“跳过”提交。当然,在交互式变基中,您可以让它跳过一些提交,但是很明显您打算这样做。)c2c4
未标记的(“不可见”或“隐藏”)提交只要保留在引用日志中(90 天,除非您更改默认设置),就会一直存在。为了使它们停留更长时间,请设置一个标签\xe2\x80\x94(例如分支或标记名称\xe2\x80\x94)来指向它们。这就是我对temp上面标签所做的事情。现在它们再次可见,并且可以在任何提交树查看器中轻松查看,例如gitk或git log中轻松查看。
(如果您要求交互式变基“压缩”多个提交,它只是将更改折叠到一个提交中。由于每个新提交都是一个副本\xe2\x80\x94a“重播”,就像\xe2\x80\ x94很容易将更多更改堆叠在一起,将它们全部作为一个压缩提交提交。如果您省略某个提交,它只会跳过它,仅复制其余的。如果您重新排序提交,它只会复制它们按照新的顺序排列。)
\n\n1它的拼写方式还有很多。事实上,git log HEAD..temp尽管看起来是错误的,但不知何故,它确实奏效了。:-) 这些版本都假设这HEAD仍然是您进行变基操作的分支的名称。例如,如果您在分支机构,squiggle则可以使用git log temp ^squiggle, 一旦移动到其他地方。HEAD