简体   繁体   English

破碎的Git树

[英]Broken Git Tree

I recently inherited a project and found out that the git repo tree is broken. 我最近继承了一个项目,发现git repo树坏了。 在此输入图像描述

The first blue commit contains ALL the code of the app plus some changes in the commit. 第一个蓝色提交包含应用程序的所有代码以及提交中的一些更改。

I have two questions. 我有两个问题。

  1. How is such a state created? 这样的国家是如何创造的?
  2. Is it possible to fix this tree. 是否可以修复此树。 Perhaps Push the head of the blue sub branch on the red master branch? 也许将红色分支的头部推到红色主分支上?

Any ideas would be appreciated. 任何想法,将不胜感激。

Unrelated histories can be joined together using git filter-branch . 可以使用git filter-branch将不相关的历史连接在一起。 Here's an excerpt from the manpage: 以下是该联机帮助页的摘录:

To set a commit (which typically is at the tip of another history) to be the
parent of the current initial commit, in order to paste the other history behind
the current history:

    git filter-branch --parent-filter 'sed "s/^\$/-p <graft-id>/"' HEAD

(if the parent string is empty - which happens when we are dealing with the
initial commit - add graftcommit as a parent). Note that this assumes history
with a single root (that is, no merge without common ancestors happened). If
this is not the case, use:

    git filter-branch --parent-filter \
            'test $GIT_COMMIT = <commit-id> && echo "-p <graft-id>" || cat' HEAD

or even simpler:

    git replace --graft $commit-id $graft-id
    git filter-branch $graft-id..HEAD

In your case, $commit-id is the first blue commit and $graft-id is the last red. 在你的情况下, $commit-id是第一个蓝色提交, $graft-id是最后一个红色。


Here's an example of the complete procedure: 以下是完整程序的示例:

Let's create a repo and some red commits: 让我们创建一个repo和一些红色提交:

$ git init
$ echo a >a
$ git add a
$ git commit -m c1
[master (root-commit) 6a6b98f] c1
 1 file changed, 1 insertion(+)
 create mode 100644 a
$ echo b >>a
$ git add a
$ git commit -m c2
[master d91d385] c2
 1 file changed, 1 insertion(+)

Now create an unrelated branch o1 and add some blue commits: 现在创建一个不相关的分支o1并添加一些蓝色提交:

$ git checkout --orphan=o1
Switched to a new branch 'o1'
$ echo c >>a
$ git add a
$ git commit -m c3
[o1 (root-commit) ed2b106] c3
 1 file changed, 3 insertions(+)
 create mode 100644 a
$ echo d >>a
$ git add a
$ git commit -m c4
[o1 5b655a6] c4
 1 file changed, 1 insertion(+)

Check that we got what we wanted: 检查我们得到了我们想要的东西:

$ git log --format=short --graph --all
* commit 5b655a615f8a729c123d89180ca1928451b465b2 (HEAD -> o1)
| 
|     c4
| 
* commit ed2b106d7bd0ffef317a723f2921808bc8ad9f45

      c3

* commit d91d385c7811ba07f4092133c435b55323562686 (master)
| 
|     c2
| 
* commit 6a6b98fca7150839f607d9d55c6b9f10861375f8

      c1

Create a graft commit for ed2b106 (c3, first blue) with d91d385 (c2, last red) as its new parent: 使用d91d385 (c2,最后一个红色)作为新父级创建ed2b106 (c3,第一个蓝色)的移植提交:

$ git replace --graft ed2b106d7bd0ffef317a723f2921808bc8ad9f45 d91d385c7811ba07f4092133c435b55323562686
$ git log --format=short --graph --all
* commit 5b655a615f8a729c123d89180ca1928451b465b2 (HEAD -> o1)
| 
|     c4
| 
* commit ed2b106d7bd0ffef317a723f2921808bc8ad9f45 (replaced)
| 
|     c3
|   
| * commit 4656e5bca003770b1a35aff10e3ffb51f7fb1ad9
|/
|       c3
| 
* commit d91d385c7811ba07f4092133c435b55323562686 (master)
| 
|     c2
| 
* commit 6a6b98fca7150839f607d9d55c6b9f10861375f8

      c1

We got 4656e5b (fixed c3) as a replacement with fixed parents, but that replacement is only local, so we now need to rewrite all the blue commits: 我们得到4656e5b (固定的c3)作为固定父母的替代品,但是那个替换只是本地的,所以我们现在需要重写所有的蓝色提交:

$ git filter-branch d91d385c7811ba07f4092133c435b55323562686..HEAD
Rewrite 5b655a615f8a729c123d89180ca1928451b465b2 (2/2) (0 seconds passed, remaining 0 predicted)    
Ref 'refs/heads/o1' was rewritten
$ git log --format=short --graph
* commit 2cf6b0d3a0ee2deff99bbe327d065f90c82c1c2b (HEAD -> o1)
| 
|     c4
| 
* commit 4656e5bca003770b1a35aff10e3ffb51f7fb1ad9
| 
|     c3
| 
* commit d91d385c7811ba07f4092133c435b55323562686 (master)
| 
|     c2
| 
* commit 6a6b98fca7150839f607d9d55c6b9f10861375f8

      c1

The 4656e5b (fixed c3) was already good (same as ed2b106 , the original c3, just with different parent), but 5b655a6 (c4) was rewritten so that its parent is 4656e5b (fixed c3) instead of ed2b106 (original c3). 4656e5b (固定的c3)已经很好(与ed2b106相同,原始c3,只是与不同的父级),但是5b655a6 (c4)被重写,因此其父级是4656e5b (固定c3)而不是ed2b106 (原始c3)。 We can now safely drop the replacement as ed2b106 is no longer used in our history: 我们现在可以放心更换,因为ed2b106已不再用于我们的历史:

$ git replace -d ed2b106d7bd0ffef317a723f2921808bc8ad9f45
Deleted replace ref 'ed2b106d7bd0ffef317a723f2921808bc8ad9f45'

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM