That is有点不寻常,但你的诊断是正确的。
交互式变基使用一系列git cherry-pick
命令。非交互式变基使用git-merge-recursive
(至少默认情况下;请参阅git-rebase--merge
脚本中的git-core
目录,无论它位于系统上的任何位置,或者只需记下-s <strategy>
论证git rebase
)从旧的提交中进行每一次新的提交。作为文档-m
/ --merge
说(尽管它没有提到这是default):
Use merging strategies to rebase. When the recursive (default)
merge strategy is used, this allows rebase to be aware of renames
on the upstream side.
Note that a rebase merge works by replaying each commit from the
working branch on top of the <upstream> branch. Because of this,
when a merge conflict happens, the side reported as ours is the
so-far rebased series, starting with <upstream>, and theirs is the
working branch. In other words, the sides are swapped.
You can tell for sure by using git diff -M --name-status
1 to compare the suspect commit pair. If this shows bar.js
as D
eleted and foo.js
as R
enamed to bar.js
, that's the culprit.
令人烦恼的是,无法设置合并的重命名阈值。幸运的是,解决方法只是运行交互式变基并且不对命令系列进行任何更改,您可以通过执行以下操作来简化操作:
GIT_EDITOR=: git rebase -i ...
或通过使用-p
保留合并的选项(如果有合并,后者会有所不同,但具有执行“隐式交互式”变基的副作用,它只是设置GIT_EDITOR=:
并且还关闭自动挤压)。
1The -M
option is not required if you have configured diff.renames
to true
(see git config documentation https://www.kernel.org/pub/software/scm/git/docs/git-config.html). Merge-recursive internally sets the rename but not copy detection, and sets the "rename limit" the first of whichever of these applies: your configured merge.renamelimit
, if you have one; your diff.renamelimit
if you have one; or the constant 1000
.