如何正确地强制推送(force push)
强推的正确姿势是 git push --force-with-lease:推送前校验远程分支没有别人新推的提交,比 --force 安全。强推用于 rebase/amend 后更新个人分支;共享分支禁用。步骤:fetch 确认 → --force-with-lease → 通知协作者。
用 --force-with-lease 代替 --force:它在覆盖前先检查远程分支是否仍是你上次 fetch 看到的状态——期间有人推了新提交则拒绝,不会悄悄覆盖别人的工作。这是强推的"安全带"。
正确流程
# 1. 改写历史(rebase / amend 完成后)
git rebase -i HEAD~3
# 2. 推送前看一眼远程现状
git fetch
git log HEAD..origin/feature-x --oneline # 应为空(远程没有你不知道的提交)
# 3. 带租约强推
git push --force-with-lease
--force vs --force-with-lease
| --force | --force-with-lease | |
|---|---|---|
| 覆盖远程 | 无脑覆盖 | 远程有新提交时拒绝 |
| 适用 | 明确独占的分支 | 一切需要强推的场景 |
| 风险 | 冲掉他人工作 | 几乎无 |
强推的规矩
- 共享分支不强推:main/release 永远走 revert;
- 个人分支随意:rebase 自己的 feature 分支后强推是标准工作流;
- 推前打招呼:即使个人分支被同事检出过,强推前说一声,他们需要
git reset --hard origin/分支对齐。
常见问题(FAQ)
Q:--force-with-lease 还是失败了?
说明远程确实有新提交。git log HEAD..origin/分支 看看是什么——是别人的就 merge/rebase 进来,确认可弃再推。
Q:GitHub 上保护分支不允许强推怎么办?
保护分支就是设计成不可强推的。需要"撤销"已推送内容时用 git revert 正向操作;确需强推要找管理员临时解除保护。
Q:能设置默认用 --force-with-lease 吗?
Git 没有 push.useForceWithLease 这个配置项。需要时显式使用 --force-with-lease;不要认为它改变了 git push -f 的行为。后台 fetch 可能更新跟踪引用,重要操作可以指定期望的远程提交哈希,并核对将被覆盖的提交。