git-commit 子命令可以用来创建一个 commit, 一个 commit 指向一个 tree 对象,并且包含开发人员手工编写的修改记录文本信息以及时间戳。
有时会遇到这种情况,那就是此次创建的 commit 指向的 tree 和父 commit 指向的 tree 的差异过大,导致这种情况的原因主要是编码人员在一次 commit 中积攒了太多的变更,这种情况会导致诸多坏处,包括不限于:
为了重新得到一个清晰、合理的提交历史记录,我们希望对现已创建的 commit 进行重新组合,或者是对任意相邻的已经创建好了的 commit 进行重新组合,我们将演示如何通过灵活地应用 git-checkout, git-branch, git-rebase 等一系列 git 子命令来快速实现这一需求。
理想的历史提交记录应该是这样的,即每个提交对应一个独立的修改主题,提交与提交之间的改动内容从语义上来说互不重合,或者说提交与提交之间的主题的界限尽可能清晰明确。
假设现在需要实现两个功能/需求/变更,分别记做 A, B, 假设现在有 a, b, c 三个文件,假设功能 A 的实现需要修改文件 a 和 文件 b, 功能 B 的实现需要修改文件 c, 现在,对比这两个不同的提交历史记录:
显然,第 2 种提交历史记录优于第 1 种提交历史记录,并且第 2 种更加接近理想的提交历史记录。
对于第 1 种提交历史记录已经造成了的情形,可以尝试使用 git-rebase 结合其他子命令的方式来对提交历史记录进行重新组合,这也是本文主要讲述的。
作为演示,我们先创建一个空文件夹,然后进入到该演示目录,初始化 git 仓库并且创建三个文件:
mkdir git-rebase-demo
cd git-rebase-demo
git init
echo "// file1.js" >> file1.js
echo "// file2.js" >> file2.js
echo "// file3.js" >> file3.js