第35章 更多版本控制系统的迁移
35.1 SVN版本库到Git的迁移
Subversion版本库到Git版本库的转换,最好的方法就是git-svn。而git-svn的使用方法在前面“第26章 Git和SVN协同模型”一章中已经详细介绍过。本章的内容将不再对git-svn的用法做过多的重复,只在这里强调一下版本库迁移时的注意事项,相关git-svn的内容还请参照第4篇“第26章 Git和SVN协同模型”。
在迁移之前要确认一个问题,Subversion转换到Git库之后,Subversion还能继续使用吗?意思是说还允许向Subversion提交吗?
如果回答是,那么直接查看“第26章Git和SVN协同模型”,用Git作为前端工具来操作Subversion版本库,而不要理会下面的内容。因为下面描述的迁移步骤针对的是Subversion到Git版本库的一次性的迁移。
1.不在提交说明中出现git-svn-id标识
如果一次性、永久性地将Subverison迁移到Git库,可以选择"git-svn-id:"标识不在转换后的Git的提交日志中出现,这样根本看不出来转换后的Git库曾经用Subversion版本库维护过。
在git-svn的clone或init子命令行中使用参数:—no-metadata。Git库的配置会自动将svn-remote.noMetadata配置为1。之后执行git svn fetch时就不会在日志中产生"git-svn-id:"标识。
2.Subversion用户名到Git用户名的映射
默认转换后Git库的提交者ID为如下格式:userid<userid@SVN-REPOS-UUID>,即在邮件地址的域名处以SVN版本库的UUID代替。可以在执行git svn fetch时,通过下面的参数提供一个映射文件完成SVN用户名到Git用户名的转换。
-A<filename>,—authors-file=<filename>
即用-A或—authors-file参数给出一个映射文件,这个文件帮助git-svn将Subversion用户名映射为Git用户名。此文件的每一行定义一个用户名映射,每一行的格式为:
loginname=User Name<user@example.com>
也可以通过下面的命令在Git库的config文件中设置,这样就不必在每次执行git svn fetch时都带上这个参数。
$git config svn.authorsfile/path/to/authersfile
当设定了用户映射文件后,如果在执行git svn fetch时发现SVN的用户在该映射文件中没有定义,转换过程被中断。需要重新编辑用户映射文件,补充新的用户映射后,再重新执行git-svn命令。
3.里程碑和分支的转换
使用默认的参数执行SVN到Git的转换时,SVN的里程碑和分支转换到Git库的refs/remotes引用下。这会导致其他人从转换后的Git库克隆时,看不到Subversion原有的分支和里程碑。
当以默认的参数执行git svn init时,Git的配置文件中会生成下面的配置:
[svn-remote "svn"]
fetch=trunk:refs/remotes/trunk
branches=branches/:refs/remotes/
tags=tags/:refs/remotes/tags/
可以直接编辑Git配置文件,将其内容调整如下:
[svn-remote "svn"]
fetch=trunk:refs/heads/master
branches=branches/:refs/heads/
tags=tags/:refs/tags/
之后,再执行git svn fetch后,就可以实现SVN的分支和里程碑正确地转换为Git库的里程碑。否则如果不对Git配置文件作出调整,就需要手动将.git/refs/remots/下的引用移动到.git/refs/heads及.git/refs/tags下。
4.清除git-svn的中间文件
git-svn的中间文件位于目录.git/svn下,删除此目录完成对git-svn转换数据库文件的清理。