有两个存储库A和B:
存储库A的典型工作流程是签出一个分支,将该分支合并回master,然后将master推送到源。
存储库B的典型工作流程是签出一个分支,将A.master合并到该分支中,然后将该分支推到Bs的原点。
然后将B.branch合并到A中。一段时间以来,我一直感觉自己对存储库A进行了多次更改。我认为我注意到的事情:
但是我也很清楚,因为确实出现了新代码,所以存储库B一直在合并A.master。
在尝试跟进此事时,我在存储库B中发现有一个提交,其中删除了一些代码。但是该代码似乎“重新出现”,并且记录的位置没有提交-git blame
显示原始提交消息。
这怎么可能?尽管合并了删除该代码的合并,但该代码仍显示原始提交消息?
答案 0 :(得分:1)
所有提交都是快照。
如果发现某个快照中存在某个文件,则您所知道的就是该文件存在于快照中。然后,如果它是常规提交,则必须查看其先前的快照(其 parent 提交);如果是合并提交,则必须查看其先前快照的 all (复数)。换句话说,您现在必须检查其所有直系父母。如果相同的文件以相同的形式存在于父项中,则显然是具有相同内容的相同文件。如果它以不同形式存在于父级中,则在合并期间会对其进行修改。如果它以相同或不同的形式存在于一个父级中,而另一父级中完全不存在,则它是由某人携带的,并且可能也已更改。如果它在先前的父级中不存在,那么它是在此提交中新创建的,依此类推。
对于每个提交及其所有父项重复一次,您将拥有此特定文件的历史记录,该历史记录是从此特定提交开始并向后工作的。这就是git log
和git blame
的工作方式,只是在合并中 cheat (在许多情况下是必需的)之外,它们是必需的。合并有多个父母:Git应该跟随哪个父母?如果您尝试组合一个本质上是非线性事件的线性视图,则只需舍弃,同时向后执行某些父级,提交父级,一次配对历史。
当然,丢弃父母也会阻止您查看特定工作线中的情况。这样就可以回答这个问题:
这怎么可能?尽管合并了删除该代码的合并,但该代码仍显示原始提交消息?
一些提交会引入文件:
...--o--o--+--+--+--...
({+
提交包含文件)。
后来有一些提交删除文件,但是在删除之前,其中一个提交的子文件具有文件:
...--o--o--+--+--+--o--o--...
\
+--+--...
现在,您或其他人可以使用git merge
来组合以下工作:
...--o--o--+--+--+--o--o--o--?--...
\ /
+--+--...--+--...
此合并提交(其内容为?
)具有两个父对象,其中一个具有文件(沿底部行),而另一个不具有文件(沿行)第一行)。如果合并是“正确”完成的,那么根据您的正确性标准,我认为文件应该放在?
中,因此我们来画一下:
...--o--o--+--+--+--o--o--o--o--...
\ /
+--+--...--+--...
后来,有人重新合并:
ours
v
...--o--o--+--+--+--o--o--o--o--o--?--...
\ / /
+--+--...--+--+--+--...
^ ^
base theirs
现在,在 this 合并期间,合并基础将是标记为base
的提交,--ours
提交是这样标记的,而--theirs
提交就是这样标记的。 Git将看到,在我们的工作中,我们删除了文件,他们要么更改了文件,要么没有更改。如果他们没有更改,Git的“ ?
中应该有什么”的自动答案包括保持删除的文件。如果不是(如果他们在base
和theirs
之间更改了文件,则Git的自动答案是: Help!我放弃!程序员先生,您必须自己决定结果。
如果此合并的任何人决定“保留更改的文件”,则现在返回 。如果他们决定“保留丢弃的文件”,则现在为消失。这就是?
中的新合并结果。
每个新的合并都会导致相同的问题:它们拥有文件,而我们不,合并基础也可以,并且它们可能已修改,也可能未修改。如果有人在任何时候决定保留文件的其版本,现在文件又回来了:
...--o--o--+--+--+--o--o--o--o--o--o--...--+--+
\ / / /
+--+--...--+--+--+--...--+--+
如果您是进行合并的人,那么每次他们更改文件时,您都必须决定:为得到正确的结果,我应该保留文件吗?
使用git log
可以帮助您确定某人在某个时候是否做出了错误的决定,但是通常您需要--full-history
来强制git log
沿两个路径运行。也就是说,在每次合并提交时,Git必须开始沿合并的两边进行,将每个提交与它的父项一次一对地进行比较。
没有关于谁在合并哪个提交以及如何合并的更多详细信息,很难说更多。请注意,Git提供的用于跟踪文件的工具在行分叉和重新收敛时总是会出现问题。