我对Git很新,我想我在我的主分支中造成了一团糟。
以下是发生的事情:
我正在工作(和平而且没有弄乱任何人)我得到了这样的提交。
a --> b --> C --> D
a, b
是来自其他人的提交,C
和D
是我的提交。我将所有内容推送到我们的主存储库和一个自动工具,我们必须在每次推送时运行测试表示构建失败。所以我惊慌失措。我创建了一个新目录并重新克隆了存储库,直到提交b
(当该自动化工具说构建正常时)进行了一些非常小的更改并且强制推送(是的,我不是很聪明,但已经很晚了,我吓坏了)所以在这一点上,远程存储库看起来像这样:
a --> b --> E
但事实证明我的初始提交C
和D
是正确的,并且自动化工具失败了。它给出了误报!当我意识到,有人再次提交到主分支(远程存储库),所以此时它看起来像这样。
a --> b --> E --> f
我想做的是安全而不会破坏我的同事的工作,将我的好提交C
和D
插入到分支中。我仍然在计算机的目录中进行了这些提交,但是只要我执行git pull
,它们就会被销毁。
我希望远程存储库看起来像:
a --> b --> C --> D --> f
或
a --> b --> f --> C --> D
甚至
a --> b --> E --> f --> C --> D
(保持超级虚拟提交E
,我不介意)
基本上,我想要C
和D
,而不会破坏我同事的f
提交。
这甚至可以吗?
我处于恐慌模式,所以一切都会有所帮助。
答案 0 :(得分:1)
只是做:
git pull --rebase
请注意' git pull'不会破坏你的本地提交,它会创建一个合并,这可能不是你想要的。
答案 1 :(得分:0)
你可以回复[{1}}和C
[编辑:如果你在原始回购中“丢失”它们,但我看到你没有]。使用D
按ID找到它们:
git reflog
或:
$ git reflog
(如果你在$ git reflog master
并且只想看到那里发生的变化),等等。
找到提交master
后,在其上粘贴分支标签。假设上面的输出清楚地表明D
是你想要的那个。然后:
HEAD@{3}
或:
$ git branch recover_my_stuff 'HEAD@{3}'
按编号(并使用不同的名称等)来完成。您可以在此之前运行$ git branch get_d_back 0123456
和gitk HEAD@{3}
,或gitk 0123456
等,以仔细检查这是否是您想要的那个。一旦你有分支标签,git log HEAD@{3}
和git branch
将再次显示给你。
编辑:因为你仍然在原始仓库中使用它们,所以让我们在那里工作。首先,您的gitk --all
目前有master
序列。我们将此分支重命名为a - b - C - D
,然后使用temp
获取远程仓库的最新信息,并创建一个跟踪git fetch
的新master
:
origin/master
(此处$ git branch -m master temp
$ git fetch origin
$ git checkout -b master --track origin/master
- 因为它只是原始temp
的重命名 - 也会“跟踪”master
,所以git会告诉你它与{{1}不同几个提交都是前后两个。但你不需要关心,你可以忽略git中的这些注意事项。如果你愿意,你可以通过编辑git配置来停止“跟踪”,但它会全部无论哪种方式都无害。)
好的,所以,假设你已完成上述工作,origin/master
现在显示(以更漂亮的图形形式)。我将使用分支标签origin/master
作为已恢复的内容,并假设其余部分都在gitk
上(好吧,你说它是:-)):
temp
一般来说,在其他人身上“倒回”分支标签并不好(可以自己做这件事:-))所以让我们留下master
。你可以在任何时候a - b - E - f <-- HEAD=master, origin/master
\
C - D <-- temp
添加一个简单地取消E
所做的任何提交。您现在需要做的就是在git revert
之上移植E
和C
的副本。这就是D
的作用:它将原始提交中的更改复制到新提交。然后它移动标签。
f
现在你将拥有这个:
git rebase
(因为C和D没有标签,它们会从$ git checkout temp
$ git rebase master
消失。如果你想看到它们,你可以再次将另一个标签放回去,但是现在你不再需要它们了有副本。)
现在你所要做的只是前进a - b - E - f <-- master, origin/master
\ \
\ C'-D' <-- HEAD=temp
\
C - D [no branch label]
,你可以使用gitk --all
。首先你必须master
(有一种方法可以在没有中间步骤的情况下做到这一点,但让我们保持简单):
git merge
这是相同的提交图,我们刚刚更改了HEAD指向(掌握)并删除了不可见的提交。
git checkout master
$ git checkout master
a - b - E - f <-- HEAD=master, origin/master
\
C'-D' <-- temp
op将“快进”master,因为实现合并所需的唯一事情就是“将标签向下滑动”从提交$ git merge temp
提交到merge
:
f
现在,您可以D'
删除临时分支,并a - b - E - f <-- origin/master
\
C'-D' <-- HEAD=master, temp
进行推送。
旁注:祝贺我们提供了现在提交图表的清晰示例,以及您希望它看起来像什么。这大约是确定要使用哪些git命令所需的所有工作的80%。 : - )