我有一个存储库,我正在使用mq补丁队列进行未完成的更改。补丁队列也受版本控制。
假设我有2个补丁p1和p2(按此顺序应用)。现在我对p1进行了更改:
hg qnew p1
...
hg qnew p2
...
hg qref
hg com --mq -m"(Commit before reject)"
hg qpop p1
{make change}
hg qref
hg qpush -a
...并且p2无法应用。
现在标准的方法是手动应用被拒绝的帅哥。一世 想要使用像MqMergePatch这样的东西很好并使用合并 mercurial - 但它基于已弃用的功能:
hg qsave // deprecated: use "hg rebase" instead
我的问题是:如何使用 hg rebase ?
修改
在看过存储库的日志之后,我根本不喜欢MqMergePatch对它做的事情。我使用补丁程序的主要目标是使存储库的历史记录清晰,并且不会散布无用的细节。
答案 0 :(得分:15)
我认为使用hg rebase
的建议具有误导性。 MqMergePatch页面表示它是对MqMerge的修改,这是一种在其他地方提取的新变更集之上修改一系列补丁的技术。
但是,它涉及保存已应用的修补程序队列的副本(实际上都是hg qsave does
),并使用保存的副本作为影响修补程序队列rebase的3向合并的参考的一部分。在我启用rebase扩展之前,我曾经自己这样做。然后,只需要在tip改变集之上重新设置第一个补丁我想成为它的新父级。
这不是你想要的,因为你想要的是基本上修改你改变的补丁之上的补丁。但是,修补程序队列是线性的,只有在应用了修补程序集的变更集具有与修补程序队列平行的其他子项时,才可以修改该修补程序:
--- A -------- patch1 --- patch2
\
\-- B
在上述情况下,修补程序队列可以在B
上轻松地使用hg rebase
进行重新设置(因此建议使用hg rebase
),但这与您的情况无关
处理您的情况
这是一个已应用的修补程序,其未保存的本地更改将与未应用的修补程序冲突:
--- A --- patch1 <patch2>
\
\-- [changes]
通常我会咬紧牙关并手动处理拒绝,因为它们通常很少。我发现,如果我的情况是手动处理的拒绝太多,我可能不会在第一时间正确地组织它们。
如果使用qsave
和qpush -m
等的技术优于以下内容,unlikely qsave
将很快删除qrefresh
,甚至虽然它已被弃用。
如果我真的想利用3向合并工具,我将如何处理上述情况:
(TortoisHg 2.x不允许我们修改补丁队列,所以这是我有时会做的finish-rebase-import的变种。)
使用qnew
代替--- A --- patch1 --- patch1b <patch2>
,使未保存的更改成为新补丁:
--- A --- B --- C <patch2>
将这些补丁完成为常规变更集:
patch
更新到B
将干净地应用的变更集(--- A --- B --- patch2
\
\-- C
),并应用补丁:
patch2
在C
顶部重新patch2
,以便使用3方合并来解决本地 C
与其他}之间的冲突em> B
使用 base patch2
:
(我必须在TortoiseHg 2.x中通过在重新定位之前完成--- A --- B --- C --- patch2
,然后将其重新导入队列来执行此操作。)
B
再次将C
和--- A --- patch1 --- patch1b --- patch2
作为补丁导入队列:
patch2
弹出patch1b
和patch1b
,然后将patch1
折叠为patch1new
(重命名为--- A --- patch1new <patch2>
):
patch2
现在patch1new
将完全适用于{{1}}。
答案 1 :(得分:1)
我最近一直致力于扩展这项工作,因为我一直在使用大量的MQ补丁。该扩展名称为qsmooth
(因为您&#34;平滑&#34;您的补丁)。
您可以在此处查看:https://bitbucket.org/jwdevel/qsmooth
它使用的程序与Joel's answer中的程序非常相似。 我还没有在生产中使用它,但它有相当多的测试,我很高兴收到错误报告。