git图解2:代码回退

图片描述

关于 git 的基本理解, 在第一篇git文章已介绍。 上一篇文章主要讲解了git的提交操做, 本篇在上篇基础上着重写git代码的逆向操做:代码回退。网上关于git回退的文章比较多, 本文是我的理解实践的汇总, 不当、不全之处请评论区指出。
首先,回顾下git代码存在的5个区域, 分别是 工做区间工做现场缓存区(或叫暂存区)、本地仓库(或叫当前分支)、远程仓库(或叫远程分支);以下图:
图片描述html

1.缓存区代码覆盖工做区代码

场景: 缓存区存有上次改动代码,即以前有执行:git

git add

当前工做区间代码想废弃, 可将缓存区中代码覆盖之:github

clipboard.png

对应指令:segmentfault

// 将缓存区某一文件代码 覆盖本地工做区: 
git checkout -- testReset.txt

// 将匹配的文件覆盖:
git checkout -- *.txt

// 将全部文件覆盖:
git checkout -- .

2.本地仓库代码覆盖缓存区代码

场景:发现以前add的文件不须要了,又不想工做区间从新改回去。缓存

clipboard.png

对应指令:编辑器

// 将本地仓库某一文件覆盖缓存区: 
git reset HEAD testReset.txt 

// 将匹配的文件覆盖缓存区:
git reset HEAD *.txt

// 将全部文件覆盖缓存区:
git reset HEAD .

注意: 改变的是缓存区代码, 工做区间代码不变(编辑器代码不会改变)学习

3.本地仓库代码覆盖工做区代码(经常使用)

上述两场景在实际开发中没那么经常使用,接下来 本地仓库 代码 覆盖 工做区间 代码 则常常会用到。
场景: 当前 工做区间 代码混乱(通常更新或合并分支后) , 废弃当前改动;测试

clipboard.png

对应指令:网站

// 将本地仓库某一文件代码 覆盖本地工做区: 
git checkout head testReset.txt

// 将本地仓库全部文件代码 覆盖本地工做区:(谨慎操做):
git checkout head .

咱们知道本地仓库中有一个commit列表, 记录了全部commit的记录, 查看commit列表指令:spa

// 查看commit id, 查看提交记录(git commit的记录)
git log 
git log --pretty=oneline 

// 查看以往提交历史(包括 撤销回退 记录) 
git reflog

clipboard.png

根据commit列表, 工做区间代码能实现更灵活的回退:

// 本地工做区间代码 回退到上一次版本、上上次、前10个版本 
git reset --hard HEAD^ 
git reset --hard HEAD^^ 
git reset --hard HEAD~10 

// 本地工做区间代码 回退到指定版本(“d362816”为commit id) 
git reset --hard d362816

4.远程仓库代码覆盖本地仓库代码(清除 未push 的commit)

场景: 有时候合并分支、切换分支、更新代码会致使提交絮乱的问题(没使用--rebase方式),具体体如今自动生成了commit且工做区间 代码不少冲突。使工做区间代码跟线上代码一致且删除新生成的commit。

clipboard.png

对应指令:

// 本地工做区间代码回退到远程版本 
git reset –-hard origin/master

写到了git reset指令, 就不得不说下它与 git revert 的区别:

  1. git revert是用一次新的commit来回滚以前的commit,git reset是直接删除指定的commit。

  2. 在回滚这一操做上看,效果差很少。可是在往后继续merge之前的老版本时有区别。由于git revert是用一次逆向的commit“中和”以前的提交,所以往后合并老的branch时,致使这部分改变不会再次出现,可是git reset是直接把某些commit在某个branch上删除,于是和老的branch再次merge时,这些被回滚的commit应该还会被引入。

  3. git reset 是把HEAD向后移动了一下,而git revert是HEAD继续前进,只是新的commit的内容和要revert的内容正好相反,可以抵消要被revert的内容。

git reset 与 git revert区别图:

clipboard.png

clipboard.png

5.远程仓库代码回滚(线上代码回滚)

场景: 提交了一个commit(该提交包含不少文件), 发现有问题, 须要回滚, 将线上分支(master)回滚到上一次commit;
网上有删除分支进行线上代码回滚的教程, 那种操做其实很危险, 由于通常线上的分支是master分支, 而这个分支不容许删除。
合理一些的是使用 git reset或git revert方式进行回滚;
git reset方式图解:

clipboard.png

git revert方式图解:

clipboard.png

咱们可使用git revert将新的commit替换掉;(不用git reset而用git revert的缘由是保留commit方便后续代码恢复)
对应指令:

// 替换掉上次提交的代码文件(上次的commit记录会保留)
git revert HEAD
git commit -m "回滚上次commit"
git push origin master

参考资料:
时光机穿梭 - 廖雪峰的官方网站
GitHub - wteam-xq/testGit: git学习、博文测试工程
Git HowTo: revert a commit already pushed to a remote repository

相关文章:
git图解1:git 代码区域总结;
git图解3:git分支操做;

相关文章
相关标签/搜索