如何在 Git 中合并之前对单个文件进行变基?
How to rebase individual files before merging in Git?
所以这是我们在拥有大量开发人员的公司中时不时遇到的问题:有一个功能分支合并到开发分支的拉取请求。在代码审查时,我们注意到某些文件不应合并,因为错误地针对这些文件的旧版本进行了更改,现在不需要这些文件。还有其他不同的场景,我们需要从合并中排除一些文件,以及我们希望丢弃或重新设置开发分支中的更改的更改。似乎没有简单的方法可以做到这一点,我尝试创建一个新分支并从功能分支中挑选,但当功能分支太大时,即使这样也不容易。
有没有什么简单的方法可以用开发中的文件重置单个文件并放弃这些更改?
基本上有两种方法可以解决这个问题。哪一个最好取决于您的工作流程,所以我将对它们进行解释:
添加更多提交以恢复更改
您可以只在分支的顶部添加一个或多个提交,以撤消所有不被合并的更改。在这种情况下,您可能希望开始将开发分支中的更改合并到功能分支中以使用最新版本。
由于您特别要求排除完整文件,您可以使用此命令将文件重置为开发版本:
git checkout develop -- path/to/file
这会将 develop 中的文件版本放入您的索引中。使用 git diff --cached
查看将更改的内容,如果您需要这些更改,您可以提交它们或根据需要调整它们。
这种删除更改的方式将保留功能分支中发生的历史记录。如果您在以后的提交中记录了该决定,那么这有助于理解为什么您没有按照最初的计划去做。
重新定位功能分支
您还可以通过更改其历史记录来修复您的功能分支。注意:如果分支已经与其他人共享,则更改分支的历史不是一个好主意。当分支的新旧版本合并时,git 无法识别它之前是相同的,您将得到两个版本的混合。如果你这样做,你需要确保旧版本的分支被丢弃。
从第一个案例合并开发的类比是做(当你的功能分支被签出时)
git rebase develop
这类似于创建一个新分支并cherry-pick
从功能分支中提取所有提交。如果发生冲突,系统会提示您解决。
之后您可能需要编辑您的一些提交以删除您不再需要在功能分支中进行的更改。
一种方法是交互式变基。如果你这样做 git rebase -i develop
,你会得到一个来自你的功能分支的所有提交的列表,前缀为 "pick"。这意味着此提交将按原样使用。对于要更改的那些提交,您可以将 "pick" 更改为 "edit"。 Git 然后将应用一个又一个提交,并在应用您要编辑的那些之前停止。您现在可以调整此提交的更改,提交它们(将提供原始消息)并继续使用 git rebase --continue
.
进行变基
如果您现在开始要更改什么,您也可以从 git rebase -i develop
开始,这会将两个步骤合二为一。
还有很多方法可以更改您的历史记录。例如。您可能想查看选项 --fixup
for git commit
和 --autosquash
for git rebase
,这允许您添加修复旧提交的新提交并自动联合他们。
所以这是我们在拥有大量开发人员的公司中时不时遇到的问题:有一个功能分支合并到开发分支的拉取请求。在代码审查时,我们注意到某些文件不应合并,因为错误地针对这些文件的旧版本进行了更改,现在不需要这些文件。还有其他不同的场景,我们需要从合并中排除一些文件,以及我们希望丢弃或重新设置开发分支中的更改的更改。似乎没有简单的方法可以做到这一点,我尝试创建一个新分支并从功能分支中挑选,但当功能分支太大时,即使这样也不容易。
有没有什么简单的方法可以用开发中的文件重置单个文件并放弃这些更改?
基本上有两种方法可以解决这个问题。哪一个最好取决于您的工作流程,所以我将对它们进行解释:
添加更多提交以恢复更改
您可以只在分支的顶部添加一个或多个提交,以撤消所有不被合并的更改。在这种情况下,您可能希望开始将开发分支中的更改合并到功能分支中以使用最新版本。
由于您特别要求排除完整文件,您可以使用此命令将文件重置为开发版本:
git checkout develop -- path/to/file
这会将 develop 中的文件版本放入您的索引中。使用 git diff --cached
查看将更改的内容,如果您需要这些更改,您可以提交它们或根据需要调整它们。
这种删除更改的方式将保留功能分支中发生的历史记录。如果您在以后的提交中记录了该决定,那么这有助于理解为什么您没有按照最初的计划去做。
重新定位功能分支
您还可以通过更改其历史记录来修复您的功能分支。注意:如果分支已经与其他人共享,则更改分支的历史不是一个好主意。当分支的新旧版本合并时,git 无法识别它之前是相同的,您将得到两个版本的混合。如果你这样做,你需要确保旧版本的分支被丢弃。
从第一个案例合并开发的类比是做(当你的功能分支被签出时)
git rebase develop
这类似于创建一个新分支并cherry-pick
从功能分支中提取所有提交。如果发生冲突,系统会提示您解决。
之后您可能需要编辑您的一些提交以删除您不再需要在功能分支中进行的更改。
一种方法是交互式变基。如果你这样做 git rebase -i develop
,你会得到一个来自你的功能分支的所有提交的列表,前缀为 "pick"。这意味着此提交将按原样使用。对于要更改的那些提交,您可以将 "pick" 更改为 "edit"。 Git 然后将应用一个又一个提交,并在应用您要编辑的那些之前停止。您现在可以调整此提交的更改,提交它们(将提供原始消息)并继续使用 git rebase --continue
.
如果您现在开始要更改什么,您也可以从 git rebase -i develop
开始,这会将两个步骤合二为一。
还有很多方法可以更改您的历史记录。例如。您可能想查看选项 --fixup
for git commit
和 --autosquash
for git rebase
,这允许您添加修复旧提交的新提交并自动联合他们。