当前位置:  开发笔记 > 编程语言 > 正文

撤消git rebase

如何解决《撤消gitrebase》经验,为你挑选了10个好方法。

有谁知道如何轻松撤消git rebase?

想到的唯一方法是手动进行:

git checkout两个分支的提交父级

然后从那里创建一个临时分支

樱桃 - 手工挑选所有提交

用手动创建的分支替换我重新定位的分支

在我目前的情况下,这是可行的,因为我可以很容易地发现两个分支的提交(一个是我的东西,另一个是我的同事的东西).

然而,我的方法让我感到不理想和容易出错(假设我刚刚用自己的2个分支重新定位).

有任何想法吗?

澄清:我正在谈论一个rebase,在此期间重播了一堆提交.不仅仅是一个.



1> CB Bailey..:

最简单的方法是找到分支的头部提交,就像在reflog中启动rebase之前一样...

git reflog

并将当前分支重置为它(通常在使用该--hard选项重新设置之前绝对确定).

假设旧提交HEAD@{5}在ref日志中:

git reset --hard HEAD@{5}

在Windows中,您可能需要引用引用:

git reset --hard "HEAD@{5}"

您可以通过执行a git log HEAD@{5}(Windows :)来检查候选旧头的历史记录git log "HEAD@{5}".

如果你没有禁用每个分支reflogs,你应该能够简单地做,git reflog branchname@{1}因为rebase在重新连接到最终头之前分离分支头.我会仔细检查这个,尽管我最近没有证实这一点.

默认情况下,为非裸存储库激活所有reflog:

[core]
    logAllRefUpdates = true


以防万一,首先进行备份:`git tag BACKUP`.如果出现问题你可以返回它:`git reset --hard BACKUP`
Git reflog很棒,只记得你可以用`git log -g`获得更好的格式化输出(来自Scott Chacon的http://progit.org/book).
@Zach:`git rebase --abort`(`-i`对`--abort`毫无意义)是放弃一个尚未完成的rebase - 要么是因为存在冲突,要么是因为它是交互式的,或者两者兼而有之; 这不是要取消成功的变革,这就是问题所在.您可以使用`rebase --abort`或`reset --hard`取决于您所处的情况.您不应该同时执行这两种操作.
如果你做了很多提交,那么你要找的HEAD @ {#}将以`commit:`开头,而不是`rebase:`.听起来很明显,但它让我有点困惑.
在意外变装后参加聚会:D.在意外重组之后,"git reset - hard ORIG_HEAD"不会立即行动吗?

2> Pat Notz..:

实际上,rebase会保存你的起点,ORIG_HEAD所以这通常很简单:

git reset --hard ORIG_HEAD

reset,rebasemerge所有的原始保存HEAD指针变成ORIG_HEAD这样,如果你因为你试图撤消,那么你就必须使用引用日志底垫做过任何的命令.


如果'ORIG_HEAD`不再有用,你也可以使用`branchName @ {n}`语法,其中`n`是分支指针的第n个先前位置.因此,例如,如果你将`featureA`分支重新绑定到你的`master`分支,但是你不喜欢rebase的结果,那么你可以简单地执行`git reset --hard featureA @ {1}`来重置分支回到你做rebase之前的确切位置.您可以在[官方Git docs for revisions](http://git-scm.com/docs/gitrevisions)上阅读有关@ {n}分支语法的更多信息.
这是最简单的.然后使用`git rebase --abort`跟进它.
@Seph你能解释为什么你建议跟进`git rebase --abort`吗?
让我补充一下:`git reset --hard ORIG_HEAD`可以反复使用以一次又一次地回滚。假设,如果A ---重新设置为B ---重新设置为C,现在我在C,则可以使用两次git reset --hard ORIG_HEAD来返回A。

3> 小智..:

查尔斯的答案有效,但你可能想这样做:

git rebase --abort

之后清理reset.

否则,您可能会收到消息" Interactive rebase already started".


那不是问题.该问题询问如何撤消已完成的rebase.
这个在我的提示中删除了"| REBASE"部分.+1

4> Aristotle Pa..:

将分支重置为其旧提示的悬空提交对象当然是最佳解决方案,因为它可以在不花费任何精力的情况下恢复之前的状态.但是,如果您碰巧丢失了这些提交(因为您在此期间垃圾收集了您的存储库,或者这是一个新的克隆),您可以再次重新绑定该分支.关键是--onto交换机.

比方说,你有一个特性分支想象力叫topic,你分支master时的尖端master0deadbeef提交.在topic分支的某个时刻,你做到了git rebase master.现在你要撤消这个.这是如何做:

git rebase --onto 0deadbeef master topic

这将采取所有提交的topic使不上master重放一遍之上0deadbeef.

有了--onto,您可以将历史重新排列成几乎任何形状.

玩得开心.:-)


我认为这是最好的选择,因为它的灵活性.我将b1从master分支出来,然后将b1重新命名为新的分支b2,然后又想将b1恢复为基于master的.我只是喜欢git - 谢谢!
这是最好的选择!它保留了我当前分支上的所有更改,并删除了所有不需要的更改!

5> Alex Gontmak..:

在我做任何非常重要的操作之前,我实际上在分支上放了一个备份标签(大多数rebase都很简单,但是如果它看起来很复杂的话我会这样做).

然后,恢复就像一样容易git reset --hard BACKUP.


你实际上甚至不需要创建备份分支,你可以简单地使用`branchName @ {n}`语法,这里`n`是分支指针的第n个先前位置.因此,例如,如果你将`featureA`分支重新绑定到你的`master`分支,但是你不喜欢rebase的结果,那么你可以简单地执行`git reset --hard featureA @ {1}`来重置分支回到你做rebase之前的确切位置.您可以在[官方Git docs for revisions](http://git-scm.com/docs/gitrevisions)上阅读有关`branch @ {n}`语法的更多信息.
我曾经也是这样做的,但是因为我对reflog更加满意,所以我不再认为这是必要的.每次更改HEAD时,reflog基本上都是代表您执行此操作.
好吧,我更喜欢有意义的名字,因为在reflog中搜索正确的项目有时根本不好玩.
我也是这样做的.git diff BACKUP..HEAD也很有用,可以确保你改变了你想要的东西.
实际上,你甚至不需要使用上面的语法,根据[Pat Notz的答案](http://stackoverflow.com/a/692763/456814),分支的原始`HEAD`暂时存储在` ORIG_HEAD`.但是使用备份分支标签的技术也有效,它只是更多步骤.

6> Maksym..:

如果您已经将分支推送到远程存储库(通常是它的原点),然后您已经完成了成功的rebase(没有合并)(git rebase --abort给出"没有正在进行的rebase"),您可以使用命令轻松地重置分支:

git reset --hard origin/{branchName}

例:

$ ~/work/projects/{ProjectName} $ git status
On branch {branchName}
Your branch is ahead of 'origin/{branchName}' by 135 commits.
  (use "git push" to publish your local commits)

nothing to commit, working directory clean

$ ~/work/projects/{ProjectName} $ git reset --hard origin/{branchName}
HEAD is now at 6df5719 "Commit message".

$ ~/work/projects/{ProjectName} $ git status
On branch {branchName}
Your branch is up-to-date with 'origin/{branchName}.

nothing to commit, working directory clean



7> Kris..:

使用reflog对我不起作用.

对我有用的东西与此处描述的类似.打开以重新分支的分支命名的.git/logs/refs中的文件,找到包含"rebase finsihed"的行,如:

5fce6b51 88552c8f Kris Leech  1329744625 +0000  rebase finished: refs/heads/integrate onto 9e460878

签出该行上列出的第二个提交.

git checkout 88552c8f

一旦确认,这包含了我失去的变化,我分支并松了一口气.

git log
git checkout -b lost_changes


哇 - 从那个链接,"有一个警告:我失去了分支的历史,但在这种情况下它并不重要.我很高兴能找回我的变化." ?

8> Greg Hewgill..:

对于多次提交,请记住任何提交都会引用导致该提交的所有历史记录.所以在查尔斯的回答中,将"旧提交"称为"最新的提交".如果重置为该提交,则会重新出现导致该提交的所有历史记录.这应该做你想要的.



9> Matheus Feli..:

根据@Allan和@Zearin的解决方案,我希望我可以简单地做一个评论,但我没有足够的声誉,所以我使用了以下命令:

而不是做的git rebase -i --abort (注意-i),我不得不简单地做git rebase --abort(没有-i).

使用两者-i--abort同时使Git向我显示使用/选项列表.

因此,此解决方案的先前和当前分支状态为:

matbhz@myPc /my/project/environment (branch-123|REBASE-i)
$ git rebase --abort

matbhz@myPc /my/project/environment (branch-123)
$



10> Sergey P. ak..:

如果您成功地针对远程分支进行了重新设置,那么git rebase --abort您仍然可以做一些技巧来保存您的工作并且没有强制推送.假设您的当前分支被错误地重新命名your-branch并且正在跟踪origin/your-branch

git branch -m your-branch-rebased #重命名当前分支

git checkout origin/your-branch #checkout到原始已知的最新状态

git checkout -b your-branch

检查git log your-branch-rebased,比较git log your-branch和定义缺少的提交your-branch

git cherry-pick COMMIT_HASH 每次提交 your-branch-rebased

推动你的改变.请注意,两个本地分支机构相关联,remote/your-branch您应该只推送your-branch

推荐阅读
有风吹过best
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有