| 
                             
                              | 
                                   
                                    | 编辑推荐: |   
                                    | 本文主要介绍了Git 提交错了也能“回锅”及到底有哪些“提交错了”的场景相关内容。希望对你的学习有帮助。 本文来自于微信公众号程序员晓帆,由火龙果软件Linda编辑、推荐。
 |  |  写代码就像炒菜,锅铲一抖盐放多了还能加水,Git 提交错了也能“回锅”。 但回锅方法不对,可能把整锅菜都糊掉。 今天咱们就掰开揉碎聊聊:到底有哪些“提交错了”的场景? 每种场景到底该怎么优雅地撤回?全部给你配好命令、画好流程,照着抄就行。 一、先分清“锅”在哪儿 Git 把仓库分成三大块: 工作区(Working Directory):你电脑上看得见的文件夹。  暂存区(Index / Stage):git add 之后放东西的地方。  本地仓库(Local Repo):git commit 之后放东西的地方。  远程仓库(Remote Repo):GitHub、GitLab、gitee 
                            等远端服务器。  搞错一次提交,先问自己一句:  “锅”现在停留在哪一层? 只在工作区?  只在暂存区?  已经 commit 但还没 push?  已经 push?  甚至 push 完别人已经拉下来继续开发了?  不同位置,撤回姿势完全不同。下面分场景,逐个拆招。 二、场景 1 症状  git add 了不该 add 的文件,比如把 node_modules 
                            也扔进去了,但还没 commit。 解决把东西从暂存区踢回工作区即可: 
                            
                              | # 全部撤回git reset HEAD .
 
 # 只撤回某个文件
 git reset HEAD package-lock.json
 
 |     add 错了,还没 commit  
                           三、场景 2 A. 只想改 commit message 
                            
                               
                                |  git commit --amend -m "新的提交说明"
 |   B. 漏了文件 
                            
                              | git add forgotten.javagit commit --amend --no-edit   # 不改动 message
 
 |     commit 写错信息,或忘了加文件  注意:amend 会生成新的 commit-id,如果已经 push 
                            过,就属于“改写历史”,需要强制推送(见后文)。 四、场景 3 最后一次 commit 想直接作废 
                            
                              | # 撤回 commit,改动保留在工作区git reset --soft HEAD~1
 # 或者
 git reset --mixed HEAD~1   # 默认模式,改动回到工作区
 
 |     连改动都不要,彻底删除 
                            
                              | # 回退 3 个提交git reset --hard HEAD~3
 
 |     流程图   ommit 错了,但还没 push  注意:--hard 会丢改动,先确认没重要代码。 五、场景 4 思路:先本地回退,再强制推送。 步骤  1)本地回退 
                            
                              | git reset --hard <回退到的commit-id>
 |   2)强制覆盖远端 
                            
                              | git push --force-with-lease origin main
 |   为什么用 --force-with-lease 而不是 --force?  前者会检查远端有没有人比你先 push,避免把同事的 commit 
                            冲掉,更安全。    已经 push,但没人基于它开发  
                           六、场景 5 此时“改写历史”会让同事陷入混乱,禁止 reset + force 
                            push。  正确姿势:用“反转提交”(revert)。 示例 
                            
                              | # 生成一个新的 commit,把错误提交的内容“反着做一遍”git revert <错误commit-id>
 git push origin main
 
 |   如果一次 revert 不够,可以连续 revert: 
                            
                              | git revert OLDEST_COMMIT^..NEWEST_COMMIT
 |   流程图  main: A-B-C-D-E(错误)  revert 后:A-B-C-D-E-F(撤销E)   已经 push,且同事已拉取并继续开发  优点:历史干净、无冲突风险;缺点:会多一个 commit,强迫症可能不爽。 七、场景 6 A. 刚 merge,发现合错分支 
                            
                              | git reset --hard HEAD~1   # 直接回到 merge 前
 |   B. merge 了很久,已产生大量后续 commit  思路:用 git revert -m 反转 merge commit。 
                            
                              | git revert -m 1 <merge-commit-id>
 |   -m 1 表示保留 merge 的第一个父分支(通常是 main)。    merge 错了,还没 push  
                            八、场景 7 rebase 过程中冲突太多,想直接放弃:  已经 rebase 完但后悔了: 
                            
                              | # 查看 reflog 找到 rebase 前的 HEADgit reflog
 git reset --hard HEAD@{2}
 
 |   
                            九、场景 8   
                            
                              | # 撤销刚 cherry-pick 的 commitgit cherry-pick --abort
 
 |   如果已经 commit,可用 revert 回滚单个 cherry-pick 
                            的 commit。    cherry-pick 错了  
                            十、万能后悔药:reflog  Git 在本地会记录每一次 HEAD 的移动。  不管 reset、rebase、merge 玩得多花,只要没 gc,都能找到“案发前”的位置。 
                            
                              | git reflog# 找到想回去的 id
 git reset --hard 9f3e2a1
 
 |   
                            十一、一张总览流程图   记住一图就行  
                            十二、踩坑小贴士  任何 reset --hard 前,先 stash 或备份分支:git 
                            branch backup。  多人协作时,默认“不能强推”,可在服务端开启保护分支。  强制推送后,通知团队所有人执行 git pull --rebase 
                            同步。  重要操作前,用 git log --oneline --graph 
                            看一眼历史,心中有数。  养成 commit 粒度细、消息清晰的习惯,能减少 80% 回滚需求。  
                            十三、记住这一句话  add 错了 reset commit 错了 amend/reset push 错了先问队友,没人用就 force,有人用就 revert。 实在搞不清,reflog 带你穿越回过去。 祝你再也不用“删库跑路”,回滚也能优雅如风。 |