git作为版本控制肯定是常见的了,对于git有一个版本回滚的功能是我们在开发过程中应该用到比较多,掌握它对于我们开发来说是非常重要的。
引言
什么叫做git的回滚尼?
我先来解释下使用场景吧!
比如我们在开发过程中有这样的需求,这里的需求是对于代码的托管,而并非开发的业务需求。
在用git做版本控制的时候,肯定会有提交错误的情况,想回到提交前的版本,或者我回到提交前的版本了,又想回到刚刚修改的版本,那么我该怎么办?
或者还有这样那样的奇葩的需求,在对于分布式的版本控制都能够满足你的需求;
在之前,我是假设我们都会git的基本语法了,如果不会,飞机票到git指南
首先,引入三个问题
- commit了一个错误版本,应该怎么回退版本?
- commit+push了一个错误版本,怎么回退远程分之的版本?
- commit+push了一个错误版本到公共远程分支,该怎么回退?
接下里,我就来解决这三个问题。
本地分支回退
现在我们来YY一下我们有一个文件叫做tjun.txt,然后目前它有三个版本的提交记录,分别是:
- create a file
create a file
- add content
add content
- change file
change
假设这就是我们的提交记录,我们可以使用git log查看我们的提交记录,
$git log
commit 834ab3343cc23e43c2435e43a324b43545e23430(commit id)
Author asw (commit author)
Date Thu Nov 30 15:55:20 2017 +0800
change filecommit 84acd3434b3348a80989ce8e3437341e23240243(commit id)
Author asw (commit author)
Date Thu Nov 30 15:50:20 2017 +0800
add contentcommit 99bf354c43544542b48f9e909c05226233bf755030(commit id)
Author asw (commit author)
Date Thu Nov 30 15:49:20 2017 +0800
create a file
git log就是用来查看最近的提交记录,如果嫌输出信息太多,看得眼花缭乱的,可以试试加上--pretty=oneline参数:
$ git log --pretty=oneline
834ab3343cc23e43c2435e43a324b43545e23430 change file
84acd3434b3348a80989ce8e3437341e23240243 add content
99bf354c43544542b48f9e909c05226233bf755030 create a file
在git中使用HEAD表示当前版本,HEAD^和HEAD~0 表示上一个版本,当然也可以根据commitId来确定版本。
重点来了:
有了这些铺垫,就可以开始操作版本回退了。
git reset --hard 834ab3343cc23e43c2435e43a324b43545e23430
这一操作就可以回退到commit id为834ab3343cc23e43c2435e43a324b43545e23430的这个版本去。
或者还有一个办法,就是根据HEAD来指定回退到哪个版本去。
git reset --hard HEAD^ 或者 git reset --hard HEAD~0 即回退到上个版本
但是,现在你又想回退到刚才未回退之前的版本,应该怎么办尼?你依然可以使用git reset --hard commitId的方式来操作,你可以使用git reflog来查看你想去的版本的commitId.
好了关于本地分支的回退操作就先说到这里。
远程分支回退
这种情况就是前面跟大家分析的第二种可能的问题,大家将本地的的分支推送到远程分支了,但是发现分支有错误,想要将远程分支回退。
git reflog
git reset --hard commit ID
git push -f origin //注意前面先操作本地分支回退,之后必须强制push,进行覆盖。
这里的有一个前提是:这个远程分支是你自己维护的远程分支,而并协作的远程分支。
最后,就来介绍下公共的远程分支,也就是协作开发时所用的远程分支。
公共远程分支回退
对于公共的远程分支,我介绍以下方式:
git revert HEAD //撤销最近一次提交
git revert HEAD~1 //撤销上上次的提交,
git revert commitId //撤销commitId这次提交
这里git revert 命令意思是撤销某次提交。但是它会产生一个新的提交,虽然代码回退了,但是版本依然是向前的,所以,当你用revert回退之后,所有人pull之后,他们的代码也自动的回退了。
给点tips
- revert 是撤销一次提交,所以后面的commitId是你需要回滚到的版本的前一次提交.
- 使用revert HEAD是撤销最近的一次提交,如果你最近一次提交是用revert命令产生的,那么你再执行一次,就相当于撤销了上次的撤销操作,换句话说,你连续执行两次revert HEAD命令,就跟没执行是一样的.
- 使用revert HEAD~1表示撤销最近2次提交,这个数字是从0开始的,如果你之前撤销过产生了commitId,那么也会计算在内的。
- 如果使用 revert 撤销的不是最近一次提交,那么一定会有代码冲突,需要你合并代码,合并代码只需要把当前的代码全部去掉,保留之前版本的代码就可以了.
git revert 命令的好处就是不会丢掉别人的提交,即使你撤销后覆盖了别人的
提交,他更新代码后,可以在本地用 reset 向前回滚,找到自己的代码,然后>拉一下分支,再回来合并上去就可以找回被你覆盖的提交了。
这里提醒一下,使用revert命令,如果不是撤销的最近一次提交,那么一定会有冲突,如下所示:
<<<<<<< HEAD //start
全部清空
第一次提交
=======
全部清空
>>>>>>> parent of c24cde7... 全部清空 //end
解决冲突很简单,但是这里和git rebase的解决冲突方式不同,因为我们只想回到某次提交,因此需要把当前最新的代码去掉即可,也就是HEAD标记的代码给清除掉,然后再提交一次就解决冲突了。
网友评论