第九周_R-Git 撤销操作全解析

203 阅读4分钟

how do i undo 'git add' before commit 这篇文章是在 stackOverflow 上面的一个高分提问,也是 Git 的入门级命令。本来想的是贴一个连接的,可是这是外网,你懂的。写这篇文章的时候是访问不到的。本人在此基础上添加更多的 git 常用场景。

应该来说想要撤销有三种情况:

  1. add 之后,未 commit ,如何撤回?
  2. commit 之后,未 push ,如何撤回?
  3. push 了,如何撤回?

在阅读以下问题之前,我们应该先明白什么是工作区?什么是暂存区?

www.liaoxuefeng.com/wiki/896043…

如何撤销 git add

一步步还原场景,并解决问题。

新建一个测试文件

在文件夹下直接新建一个 gitadd.txt 文件。

测试

在本地 Git 仓库下,如果新建一个文件,是需要先提交。一般先 git status ,查看下状态。

git status
# 所有新建的文件都是红色的。
# 会提示你使用 git add 命令
# 新建的文件都是提示你需要使用 git add 命令,使得文件可以被 commit.


git add gitadd.txt
git status
# 添加文件后,查看文件状态
# add 之后的文件都是绿色的。
# 提示你如果想要撤销,使用 git restore --staged 命令【可以使用多个文件】
# 使用上述命令后,文件又回到了最初的状态

这里除了,git 提示的 restore 命令,也可以直接使用 git reset HEAD 命令

git reset HEAD :把所有的暂存区文件都恢复成 HEAD 对应的内容,工作区继续保留

git reset --hard HEAD : 把工作区和暂存区都恢复成 HEAD 对应的内容

如何撤销一个 commit

准备测试文件

两种办法:

  1. 新建一个文件先 add
  2. 直接修改已存在的正常文件

测试

首先先看看文件状态,是待 commit 的

git commit -m '测试回退 commit'

#-m 参数后面接着 备注信息;提交所有在暂存区的内容;也可以指定内容提交

#这里一般是使用图形化界面,比如 IDEA 自带的 git 提交那一套,更方便,不用敲命令了

git status

#会提示你有内容需要 push 到服务器

注意,commit 之后并没有命令提示你该如何撤销 。但是我们应该知道 git reset

git reset HEAD~
# 会使文件回到没有 add 的状态

如何撤销一个 push

如果是在我们自己的开发分支

我们 git reset --hard 之后:

git push -f origin xx
# 强制提交到远程对应分支

如果是在集成分支:

一般是禁止 push -f 或者说是一定不能。否则另外的同事可能会导致和远程分支关联不了。

那么一般是基于不想要的 commit 去 revert 生成一个新的 commit ,再提交。

我自己一般的操作是,先把需要回退的内容先本地删除再提交。再重新 push 即可。

Git reset 详解

  • --soft 只是把 HEAD 指向的 commit 恢复到你指定的 commit ,暂存区和工作区不变
  • --hard 把HEAD,暂存区,工作区都修改为你指定的 commit 时候的文件状态
  • --mixed 默认参数,把 HEAD ,暂存区修改为指定的 commit 文件,工作区保持不变

举个栗子:刚刚的 gitadd.txt 文件只是 commit 了,我需要回退

git reset --hrad fabbec08878c6abc0ccdda
# 那么所有的代码都会回到上面这个commit ,本地新建的 gitadd.txt 也会消失
git reset xxxx
# 工作区的不会变,就是 gitadd.txt 会回到 add 之前的状态
git reset --soft xxx
# 工作区和暂存区的都不会变。就是 gitadd.txt 是 add 之后的状态

好像是有那么个问题,如果我 git reset --hard 了,但是又发现我得代码还行,我想接着用了。咋办?

你看看,这不又是一个新的知识点了吗?

思路:基于被 reset 的 commitId 切换一个新的分支。那么被 reset 的内容也会在新的分支上。

git reflog  或者  git reflog --no-abbrev  「会展示更多的详细内容」
# 上面的命令,即可找到被 reset 的 commitId 
git checkout -b <newBranchName> commitId
# 基于这个 commitId 生成一个新的分支,然后内容就都回来了,在新的分支上

有一个问题,就是新生成的分支,在远端没有对应的分支。不过这无所谓,我们只是想要‘丢失’的内容。直接将新分支 merge 到我们的开发分支就行了。

上面这个操作,在分支被删除的情况下,也能还原。

总结

git addgit commitgit push
1.git restore --staged file[可以多个文件]2.git reset [参看上面的 Git reset 详解]git reset [参看上面的 Git reset 详解]自己的分支:可以 push -f集成分支:重新提交去覆盖

总的来说,这篇文章,我比较满意。我自己在写的时候,也学会了些新内容,也把老知识更加巩固了下,实在是很赚。比如

新内容:git reset --hard 之后,如何还原?

老知识:git reset 详解。以及对各种常用命令的更加熟悉

鉴于本人知识面有限,如果有错误的地方,或者是更好的操作,你又恰好看到了。请评论或私信,大家探讨一下。