Git Reset详解与Commit合并技巧

Git Reset 三种模式 #

Git通过管理三个树来实现版本控制:

  • Working Directory - 工作目录
  • Index/Stage - 暂存区
  • HEAD - 当前commit

Reset模式对比 #

模式HEADIndexWorking Dir使用场景
--soft✅移动不变不变重写历史,保留所有修改
--mixed(默认)✅移动✅重置不变重新组织提交内容
--hard✅移动✅重置✅重置彻底回退,丢弃修改

Soft Reset #

git reset --soft HEAD~1
  • commit回退,修改保留在暂存区
  • 适合:合并commits、修改提交信息

Hard Reset #

git reset --hard HEAD~1
  • commit和修改都丢失
  • 适合:放弃实验、强制同步远程

合并多个Commits #

方法1:Soft Reset(推荐) #

# 1. 查看要合并的commits
git log --oneline -10

# 2. 找到分支起点
git merge-base main feature-branch

# 3. soft reset到起点(假设是abc123)
git reset --soft abc123

# 4. 创建新的合并提交
git commit -m "feat: 功能完整描述"

# 5. 强制推送(如果已推送远程)
git push --force-with-lease origin feature-branch

方法2:Interactive Rebase #

# 交互式rebase最近5个commits
git rebase -i HEAD~5

# 在编辑器中,将要合并的commit标记为squash(s)
# pick abc123 第一个commit
# s def456 第二个commit  
# s ghi789 第三个commit

方法3:Squash Merge #

# 合并分支时直接squash
git checkout main
git merge --squash feature-branch
git commit -m "feat: 合并后的描述"

安全建议 #

  1. 使用reflog救援

    # 查看操作历史
    git reflog
    # 恢复到某个状态
    git reset --hard HEAD@{2}
    
  2. 推送前备份

    # 创建备份分支
    git branch backup-branch
    
  3. force-with-lease vs force

    # 更安全,检查远程是否有新提交
    git push --force-with-lease
    
    # 危险,直接覆盖
    git push --force
    

实战示例 #

场景:合并feature分支的23个commits #

# 当前在feature/analytics-improvements分支
git status                          # 确保工作区干净
git reset --soft 0a24d41            # reset到分支起点
git commit -m "feat: 实现完整功能"   # 创建合并提交
git push --force-with-lease origin feature/analytics-improvements

核心理解 #

  • Soft: 温柔模式,给你重新组织的机会
  • Mixed: 让你重新选择要提交什么
  • Hard: 核弹选项,慎用

参考:Git官方文档 - git-reset