我们有一个 Subversion 设置,它相当广泛地使用 svn:externals(在一个项目中超过 5 个外部引用,虽然大多数在同一个存储库中,但一两个在不同的存储库中但仍在同一台服务器上).目前,svn:externals 属性的设置方式是它们具有引用项目的完整 URL(即“https://[server]:[port]/svn/Repository1/Projects/...)
最近,我使用 svnsync 设置了一个 SVN 镜像,它将我们的存储库备份到外部异地设施。我们需要能够从远程站点的那些镜像存储库进行只读 check out ,这在大多数情况下似乎工作正常,除了当它试图拉出外部时,它仍然引用我们的本地现场服务器。
不确定这是否是最好的方法,但我想在远程位置设置某种提交后 Hook ,这将修改 svn:externals 的属性并替换我们本地的主机名这里的服务器与那里的远程服务器的主机名。此 Hook 将在每次 svnsync 提交后运行。
理想情况下,我们希望避免修改主存储库中的 svn:externals 属性以不包含服务器名称。
有没有人遇到过这个问题?最好的方法是什么?
最佳答案
您必须了解 svn:externals
是文件的属性,修改它们需要提交。如果您有一个镜像,并且您修改了svn:external
,那么您将创建一个新的远程版本并破坏您的镜像。修订版将不再排列。
尽管在当时这似乎是个不错的主意,但 svn:externals
在项目中可能非常糟糕。想象这样一个项目:
http://vegibank.com/svn/trunk/project1
我在这个目录中有一个 svn:external
$ svn pset svn:external "^/trunk/project2/foo foo" .
我这样做是因为 foo
目录是多个项目的共享文件集。
现在,我为 project1 创建一个标签:
$ svn cp http://vegibank.com/svn/trunk/project1 http://vegibank.com/svn/tags/1.2.3
看起来不错——除了 project1/foo
目录没有标记。 它链接到 project2/foo
的主干。
我对标签的假设是标签永远不会改变,但事实并非如此。 trunk 上的 project2/foo
工作仍在进行中,这改变了我的标签所代表的内容。如果我在 1.2.3 版本中有一个错误,并且我决定检查我的标签以查看可能是什么问题,我不一定会得到我在 project1/foo
中发布的内容——我我正在从主干中获取最新信息。
处理此问题的更好方法是创建一个发布存储库,将各种项目之间通用的代码构建为某种预编译工件,并让您的项目依赖于该工件的那个版本。它最终与依赖特定版本 libz.so
的 C 程序或依赖 org.apache.commons.httpd
1.6 版的 Java 项目没有什么不同。
这将消除 svn:externals
的使用并简化您的镜像。您可以镜像发布存储库和源存储库。
如果您坚持使用 svn:external
,请不要使用完整的 URL。相反,请使用相对 URL。
例如,如果您在上面设置了 `svn:external 而不是这样:
$ svn pset svn:external "^/trunk/project2/foo foo" .
这样做:
$ svn pset svn:external "../project2/foo foo" . #property on ^/trunk/project1
现在,如果我创建一个这样的标签:
$ svn cp http://vegibank.com/svn/trunk http://vegibank.com/svn/tags/1.2.3
我正在标记 project1
和 project2
。现在,我的 svn:external
指的是 http://vegibank.com/svn/tags/1.2.3/project2/foo
。
您需要的是一种以这种方式强制执行 svn:externals 的方法,并且您可以使用预提交 Hook 来拒绝任何具有引用 的
或 svn:external
集的提交>trunkbranches
目录,但未指定实际修订版。
关于SVN post-commit hook 修改外部,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15392176/