merge
: 将修改合并至工作副本。
用法:
merge
SOURCE
[@REV
]
[TARGET_WCPATH
]
merge
[-c
M
[,N
...] |
-r
N:M
...]
SOURCE
[@REV
]
[TARGET_WCPATH
]
(拣选合并)merge
SOURCE1
[@REV1
]
SOURCE2
[@REV2
]
[TARGET_WCPATH
]
(二路 URL
合并)这种具有一个源路径且没有版本范围的合并格式称为 “完整” 合并:
svn
merge
SOURCE
[@REV
]
[TARGET_WCPATH
]
完整合并用于在下面所描述的 “功能分支” 模式中,完成 “同步” 和 “重新整合” 合并。 它查找源分支上尚未合并到目标分支的所有修改,并将它们合并到工作副本中。合并跟踪用于了解哪些修改已被合并。
SOURCE
指定要从中提取修改的分支,而 TARGET_WCPATH
指定要对其应用修改的目标分支的工作副本。 通常情况下,SOURCE
和
TARGET_WCPATH
应该分别对应于分支的根。(如果只想合并一个子树,那么子树路径必须同时包含在
SOURCE
和 TARGET_WCPATH
中;不建议这样做,要避免合并子树。)
SOURCE
通常是一个版本库 URL
路径。可选的
“@REV
” 既指定
URL
的 PEG
限定版本,也指定将要考虑合并的最新版本。如果未指定
REV
,则假定为 HEAD
版本。如果 SOURCE
是工作副本路径,则使用该路径所对应的版本库 URL
路径,“REV
”
的默认值是基准版本 BASE
(通常是最后更新到的修订)。
TARGET_WCPATH
是工作副本路径;如果省略,则通常假定为
“.
” 。但有一些特殊情况:
如果 SOURCE
是版本库 URL
路径:
如果 URL
的路径名称和 “.
” 的路径名称相同,则将差异应用于
“.
”。否则,如果在 “.
” 中找到了与 URL
具有相同路径名称的文件,则差异将应用于该文件。在所有其他情况下,目标默认为 “.
”。
如果 SOURCE
是工作副本路径:
如果源是文件,则差异将应用于该文件(对于反向合并前期的修改很有用)。
否则,如果源是目录,则目标路径默认为 “.
”。
通常情况下,使用的工作副本应该是最新的,并且是单个修订版,没有本地修改,也没有切换的子树。
“特性分支” 合并模式
这是一个经常使用的工作流程,也称为 “开发分支” 模式,在这种模式中,开发人员创建了一个分支(功能分支), 并提交实现新功能的一系列修改。开发人员也会定期合并来自父分支的所有最新更改, 以使开发分支包含这些修改并保持最新。在功能完成后,开发人员将执行一个从功能分支到父分支的合并, 以重新整合修改。
父分支 --+----------o------o-o-------------o-- \ \ \ / \ 合并 合并 合并 \ \ \ / 功能分支 +--o-o-------o----o-o----o------
从父分支到功能分支的合并称为 “同步” 或 “追赶” 合并,从功能分支到父分支的合并称为 “重新整合” 合并。
同步合并示例
............ . . 主干 (trunk) --+------------L--------------R------ \ \ \ | \ v 功能分支 (feature) +------------------------o----- r100 r200
Subversion 将在 “主干(trunk
)” 上查找尚未合并到 “功能分支(feature
)”
中的所修改。 这种情况下,它是一个版本范围,r100:200
。在上图中,L
标记合并源的左侧(trunk@100
), R
标记右侧(trunk@20
)。
L
和 R
之间的差异将应用于目标工作副本路径。在这种情况下,工作副本是整个
“功能分支(feature
)” 的一个干净的检出结果。
要执行这个同步合并,首先需要从功能分支检出一个干净的工作副本,并在其顶层目录中运行以下命令:
svn
merge
^/trunk
请注意,现在合并仅在你的本地工作副本中,并且仍需要提交到版本库,以便其他人可以看到它。 你可以查看所做的更改,并且可能必须在提交合并之前解决冲突。
重新整合合并示例
功能分支(feature
)最后一次与主干(trunk
)同步到了版本 X
。
因此,trunk@X
与 feature@HEAD
之间的差异包含实现该功能完整的修改集合,而没有其它的修改。
这些修改将被应用于主干(trunk
)。
rW rX 主干 (trunk) ------+--------------------L------------------o \ . ^ \ ............. / \ . / 功能分支 (feature) +--------------------------------R
在上图中,L
标记合并的左侧(trunk@X
), R
标记右侧(feature@HEAD
)。 左侧和右侧之间的差异被合并到了主干之中(目标)。
要执行这个合并,首先需要从主干检出一个干净的工作副本,并在其顶层目录中运行以下命令:
svn
merge
^/feature
为避免不必要的合并冲突,重新整合的合并要求 TARGET_WCPATH
不能是混合版本的工作副本, 且没有本地修改,也没有切换的子树。
重新整合合并还要求源分支与目标持续同步,在上面的示例中,这意味着分支点 W
和最后合并的版本 X
之间的所有版本都已合并到了功能分支,以便两者之间没有未合并的版本。
这种格式叫做 “拣选合并”:
svn
merge
[-c
M
[,N
...] |
-r
N:M
...]
SOURCE
[@REV
]
[TARGET_WCPATH
]
拣选合并用于从一个分支到另一个分支合并指定的版本(或版本范围)。
默认情况下,它使用合并跟踪自动跳过已经合并到目标的任何版本;可以使用
--ignore-ancestry
选项禁用此类跳过。
SOURCE
通常是一个版本库 URL
路径。可选的
“@REV
” 仅指定 URL
的 PEG
限定版本,并不影响合并范围;如果未指定 REV
,则假定为 HEAD
版本。如果
SOURCE
是工作副本路径,则使用该路径对应的版本库 URL
路径,“REV
” 的默认值是 BASE
基准版本(通常是最后更新到的版本)。
TARGET_WCPATH
是工作副本路径;如果省略,则通常假定为
“.
” 。前面 “完整合并” 格式中提到的特殊情况在此处同样适用。
要合并的版本范围由 “-r
” 和/或 “-c
” 选项指定。其中
“
” 表示源分支的版本历史中版本
-r
N:MN
和 M
之间的差异。还可以
“
” 合并单个版本:
“-c
M
” 等效于
“-c
M
”。每个这样的差异都将应用于
-r
<
M-1>
:MTARGET_WCPATH
。
如果 TARGET_WCPATH
的 mergeinfo
指出该范围内的版本已被合并,则在这些版本中所做的修改不会被再次合并。
如果需要,可以将一个范围分为多个子范围,然后分别合并每个子范围。
“反向范围” 可用于撤消修改。例如,当源和目标引用同一分支时,可以 “撤消” 先前提交的版本。
对于一个相反的版本范围,其 “
” 中的
-r
N:MN
大于 M
,或者 “-c
”
选项中使用了负数:“-c
”
等效于 “-M
”。取消这样的修改也称为执行
“反向合并”。-r
M:<
M-1>
可以指定多个 “-c
” 和/或 “-r
”
选项,并且可以混合使用正向和反向范围。
拣选合并示例
在主干分支,一个缺陷已被版本 50
所修复,这个修复需要从主干合并至发布分支。
发布分支 1.x-release +-----------------------o----- / ^ / | / | 主干 trunk ------+--------------------------LR----- r50
在上图中,L
表示合并的左侧(trunk@49
),R
表示合并的右侧(trunk@50
)。左侧和右侧之间的差异将应用于目标工作副本路径。
请注意,版本 49
和版本 50
之间的差异明显是版本 50
所提交的那些修改,不包括版本 49
所提交的修改。
要执行合并,首先需要一个发布分支的干净工作副本,并在其顶层目录中运行以下命令;请记住,默认目标是
“.
”:
svn
merge
-c
50
^/trunk
你还可以拣选几个版本和/或版本范围:
svn
merge
-c
50,54,60
-r
65:68
^/trunk
这种格式叫做 “两路 URL
合并”:
svn
merge
SOURCE1
[@REV1
]
SOURCE2
[@REV2
]
[TARGET_WCPATH
]
仅当其他格式不适用于你的情况时,才应使用此种合并格式,因为掌控该格式非常复杂。
指定两个源 URL
路径,它们分别标识同一分支或不同分支上的两棵树。比较这两棵树并将从
SOURCE1@REV1
到 SOURCE2@REV2
的差异应用于目标分支在 TARGET_WCPATH
的工作副本。目标分支可以与一个或两个源相同,也可以不同。涉及的三个分支可以完全互不相关。
TARGET_WCPATH
是工作副本路径;如果省略,则通常假定为 “.
” 。
前面 “完整合并” 格式中提到的特殊情况在此处同样适用。
SOURCE1
和/或 SOURCE2
也可以指定为工作副本路径,在这种情况下,合并源 URL
将从工作副本获取。
两路 URL 合并示例
在不同的分支 “foo
” 和 “bar
” 上分别开发了两个功能。
很明显,在重新整合之前,应将 “bar
” 与 “foo
”
分支结合起来以进行进一步开发。
尽管两个功能分支都源自主干,但它们并不直接相关 —— 其中一个不是另一个的直接副本。必须进行两路
URL
合并。
“bar
” 分支已经与主干同步至版本 500
(如果不知到这个版本号,可以使用
“svn
” 和/或
“log
svn
”
命令确定)。mergeinfo
trunk@500
和 bar@HEAD
之间的差异包含有关功能分支
“bar
” 完整的修改集合,而没有其他修改。这些修改将应用于 “foo
” 分支。
foo +-----------------------------------o / ^ / / / r500 / 主干 trunk ------+------+-----------------L---------> / \ . / \ ............ / \ . / bar +-----------------------------------R
在上图中,L
标记合并的左侧 (trunk@500
),R
标记右侧 (bar@HEAD
)。 左侧和右侧之间的差异将应用于目标工作副本路径,在这儿为
“foo
” 分支的工作副本。
要执行这个合并,首先需要一个 bar
分支的干净工作副本,并在其顶层目录中运行以下命令:
svn
merge
^/trunk@500 ^/bar
可以使用 svn
的 diff
命令来预览 2
路 URL
合并确切要应用的修改,这是一个不错的主意,
可以验证您是否没有足够干净的工作副本可以合并到其中。在这种情况下执行:
svn
diff
^/trunk@500 ^/bar@HEAD
以下内容适用于所有类型的合并:
为了防止不必要的合并冲突,svn
要求
merge
TARGET_WCPATH
不能是混合版本的工作副本。在开始合并之前运行
“svn
”
可确保工作副本中的所有项目均基于同一个版本。update
如果可能的话,在合并之前,不应在合并的目标工作副本中进行任何本地修改,以简化操作。 这样,还原合并和了解分支的历史将更加容易。
在合并过程中也应避免使用切换的子路径,因为它们可能会导致不完整的合并并创建子树的合并信息
mergeinfo
。
对于每个合并的项目,将输出一行,其中包含一些字符来报告所采取的操作。这些字符具有以下含义:
A
: 已添加D
: 已删除U
: 已更新C
: 冲突G
: 已合并E
: 已存在R
: 已替换第一列中的字符报告有关项目本身的信息。第二列中的字符报告有关项目属性的信息。 第三列中的 “C
”
表示树冲突,而第一列和第二列中的 “C
” 分别表示文件和属性值中的文字冲突。
合并跟踪
Subversion 使用 svn:mergeinfo
属性跟踪合并历史。
在合并开始时参考此属性以确定要合并的内容,并在合并结束时对其进行更新以描述所发生的合并。
仅当两个源位于同一历史记录行时才使用合并信息 Mergeinfo
——
如果第一个源是第二个源的祖先,反之亦然(即一个源最初是通过复制另一个来创建的)。
使用同步合并和重新整合合并时,将对此进行严格的验证。
--ignore-ancestry
选项可阻止合并跟踪,并忽略 mergeinfo
合并信息,既不参考也不记录。
合并外部版本库
Subversion 支持从外部版本库进行合并。尽管所有合并源 URL
必须指向同一版本库,但是合并目标工作副本可能来自与源不同的版本库。但是,会有一些警告。
最值得注意的是,在合并源中创建的副本将在合并目标中转换为普通的添加项。
另外,对于来自外部版本库的合并,不支持合并跟踪。
有效选项: | ||
---|---|---|
-r [--revision] ARG | : | 指定版本
ARG (一些命令也接受 ARG1:ARG2
格式的版本范围),版本参数可以是如下之一:
|
-c [--change] ARG |
: | 版本 ARG
(类似 ) 所作的修改:
|
-N [--non-recursive] | : | 已过时,与
--depth
相同 |
--depth ARG | : | 限制输出深度为
ARG (empty ,
files , immediates , 或
infinity ) |
-q [--quiet] | : | 不输出信息,或只输出概要信息 |
--force | : | 即使删除的内容不匹配也强制删除 |
--dry-run | : | 尝试操作,但不做任何更改 |
--diff3-cmd ARG | : | 使用
ARG 作为合并命令 |
--record-only | : | 仅合并合并信息 mergeinfo 差异 |
-x [--extensions] ARG |
: | 为外部比较、内部比较、或追溯命令指定比较选项,默认为 “-u ”。
各个选项之间使用空白分隔。外部比较和追溯命令使用的选项:
|
--ignore-ancestry | : | 禁用合并跟踪;就像相关一样比较节点 |
--accept ARG |
: | 指定自动解决冲突的措施:
|
--reintegrate | : | 不推荐使用 |
--allow-mixed-revisions | : | 允许在混合版本工作副本中执行移动操作。不建议使用此选项!请改为运行
“svn ” 来代替 |
-v [--verbose] | : | 输出详细信息 |