在我工作的地方,我们将Git用于当前项目,但我们在SVN上有一些遗留项目。我正在考虑将一些大型遗留项目(26,000多次提交)从SVN转换为Git。
但是,我遇到的问题是我们还希望保留SVN存储库。这样做的原因是部署是通过更新/切换客户端环境中存在的SVN签出来处理的:更新我们的部署脚本以使用Git,重新配置我们的所有客户端'使用Git签出等环境是一项非常重要的任务;我们认为切换到Git的好处(对所有项目都有一个具有一致拉动请求/代码审查流程的VCS)可遗传地超过了这样做所涉及的成本。
作为妥协,我们希望有一个如下所示的工作流程:
SVN只会作为此过程的一部分写入(即我们只需要在一个方向同步:Git到SVN)。
我已经看到了git svn
命令和https://github.com/nirvdrum/svn2git,并且同事已经使用此功能从SVN成功生成了Git存储库。但是,在检查了他生成的存储库(来自Github)之后,我无法轻松地将提交返回到SVN。我们原计划使用git svn dcommit
来执行此操作,但据我了解,此命令基本上要求Git存储库与SVN同步。 git svn dcommit
似乎不适用于Git存储库的新结帐:我相信这是因为git svn init
和git svn fetch
需要在dcommit
运行之前运行(请如果我错了,请纠正我。
这个问题是git svn fetch
需要天才能在这么大的存储库上运行。任何希望执行发布的开发人员都需要与SVN同步一个Git checkout,这似乎不是一个合理的选择,特别是当认为这些是将要处理的遗留项目时,但不经常。 / p>
作为dcommit
的替代方案,我编写了一个脚本来检查SVN和Git存储库,删除SVN签出的内容并将其替换为Git存储库的内容,然后提交回来到SVN。使用这种方法不会将提交的原子性和新提交的历史记录复制到SVN,但这不是问题。历史仍然存在于Git中:只要SVN反映了Git中文件的最新状态,它就不是问题。这个几乎似乎有效,但是这个脚本有一些问题产生大空白提交(用于行结束更改)和从SVN删除空目录(Git不支持提交像SVN那样的空目录)
有没有更好的方法来处理这个工作流程?如果脚本是可行的方法,您是否可以建议任何配置选项以使此过程顺利运行?我认为SVN的eol-style
和Git的core.autocrlf
设置可能可用于解决此问题(可能与{{1}等工具结合使用}),但我无法找到最好的方法。我可以用dos2unix
"占位符"修复空目录问题。文件,但这显然需要对代码进行测试,以确保这些文件可以存在而不会引起问题:还有另外一种解决方法吗?
任何建议表示赞赏。
答案 0 :(得分:0)
我还没有到达尝试恢复SVN的阶段(当我这样做的时候我已经悄悄地害怕EOL问题),但是我可以告诉你一种处理git checkout的方法所以它在大型存储库上花费的时间并不长。
诀窍是将历史记录限制在您需要的最低限度。当您想要从SVN创建git存储库时,请检查SVN日志以查找所需分支上的最新修订。如果你根本不关心历史,或者在最近的过去(通常是几天)进行一些修改,这可以是HEAD修订版。
git svn clone -r nnn:HEAD --prefix=origin/ --username=USERNAME svn://server/trunk/
关键部分是将该修订号放在nnn:HEAD
片段中。这会将该修订版中所有文件的当前状态导入git(展平历史记录),然后将每个后续SVN更改记录为单独的git修订版。对于一个非常大的存储库,或者如果您选择了较大的版本范围,这可能仍需要一两个小时,但它不应该是几天。
当然,缺点是你只有一个分支(或主干)而且只有有限的历史记录,所以如果你想进一步看,你必须使用SVN repo浏览器,如果你想在不同的SVN分支上工作,那么你必须重复这个过程(这可能是一种选择性地拼接其他SVN分支的方法,但我还没有调查过它)。但是你可以根据需要创建尽可能多的本地git分支,所以它仍然可以帮到你。
获得此初始基础后,您可以使用git svn fetch
获取新的SVN修订版,并使用git svn rebase
将这些新修订版应用于您的本地git分支。如果您正在Windows上工作,TortoiseGit会使这一点变得相当轻松。