我阅读了Git手册、常见问题解答、Git-SVN速成课程等,他们都解释了这一点和那一点,但你找不到像这样的简单说明:

SVN存储库位于:svn://myserver/path/to/svn/repos

Git存储库位于:git://myserver/path/to/git/repos

git-do-the-magic-svn-import-with-history \
svn://myserver/path/to/svn/repos \
git://myserver/path/to/git/repos

我不希望它这么简单,也不希望它是一个命令。但我确实希望它不要试图解释任何事情——只是说在这个例子中应该采取什么步骤。


当前回答

我们可以使用git-svnclone命令,如下所示。

svn log-q<svn_URL>|awk-F'|''/^r/{sub(“^”,“”,$2);sub(”$“,”,$2);print$2“=”$2“<”$2”>“}'|sort-u>authors.txt

上述命令将从SVN提交创建authors文件。

svn日志—复制时停止<svn_URL>

创建SVN项目时,上面的命令将为您提供第一个修订号。

git svn clone-r<svn_REV_NO>:HEAD--无最小化url--stdlayout--无元数据--作者文件authors.txt<svn_url>

以上命令将在本地创建Git存储库。

问题是它不会将分支和标签转换为推送。您必须手动执行这些操作。以下分支机构示例:

$ git remote add origin https://github.com/pankaj0323/JDProjects.git
$ git branch -a
* master
  remotes/origin/MyDevBranch
  remotes/origin/tags/MyDevBranch-1.0
  remotes/origin/trunk
$$ git checkout -b MyDevBranch origin/MyDevBranch
Branch MyDevBranch set up to track remote branch MyDevBranch from origin.
Switched to a new branch 'MyDevBranch'
$ git branch -a
* MyDevBranch
  master
  remotes/origin/MyDevBranch
  remotes/origin/tags/MyDevBranch-1.0
  remotes/origin/trunk
$

对于标记:

$git checkout origin/tags/MyDevBranch-1.0
Note: checking out 'origin/tags/MyDevBranch-1.0'.
You are in 'detached HEAD' state. You can look around, make experimental
changes and commit them, and you can discard any commits you make in this
state without impacting any branches by performing another checkout.

If you want to create a new branch to retain commits you create, you may
do so (now or later) by using -b with the checkout command again. Example:

  git checkout -b new_branch_name

HEAD is now at 3041d81... Creating a tag
$ git branch -a
* (detached from origin/tags/MyDevBranch-1.0)
  MyDevBranch
  master
  remotes/origin/MyDevBranch
  remotes/origin/tags/MyDevBranch-1.0
  remotes/origin/trunk
$ git tag -a MyDevBranch-1.0 -m "creating tag"
$git tag
MyDevBranch-1.0
$

现在将master、branches和标记推送到远程git存储库。

$ git push origin master MyDevBranch MyDevBranch-1.0
Counting objects: 14, done.
Delta compression using up to 8 threads.
Compressing objects: 100% (11/11), done.
Writing objects: 100% (14/14), 2.28 KiB | 0 bytes/s, done.
Total 14 (delta 3), reused 0 (delta 0)
To https://github.com/pankaj0323/JDProjects.git
 * [new branch]      master -> master
 * [new branch]      MyDevBranch -> MyDevBranch
 * [new tag]         MyDevBranch-1.0 -> MyDevBranch-1.0
$

svn2git实用程序

svn2git实用程序删除了带有分支和标记的手动工作。

使用命令sudogeminstallsvn2git安装它。之后运行以下命令。

$svn2git<SVN_URL>--authors.txt--修订版<SVN_REV_NO>

现在,您可以列出分支、标记并轻松推送它们。

$ git remote add origin https://github.com/pankaj0323/JDProjects.git
$ git branch -a
  MyDevBranch
* master
  remotes/svn/MyDevBranch
  remotes/svn/trunk
$ git tag
  MyDevBranch-1.0
$ git push origin master MyDevBranch MyDevBranch-1.0

假设您有20个分支和标记,显然svn2git将为您节省大量时间,这就是为什么我比原生命令更喜欢它的原因。这是一个很好的原生git-svnclone命令包装器。

有关完整的示例,请参阅我的博客条目。

其他回答

对于GitLab用户,我在这里提出了我如何从SVN迁移的要点:

https://gist.github.com/leftclickben/322b7a3042cbe97ed2af

从SVN迁移到GitLab的步骤

安装程序

SVN位于SVN.domain.com.au。SVN可以通过http访问(其他协议也可以)。GitLab位于git.domain.com.au,并且:与命名空间开发团队一起创建一个组。至少创建一个用户帐户,将其添加到组中,并具有用于迁移的帐户的SSH密钥(使用SSH进行测试git@git.domain.com.au).项目收藏夹项目是在开发团队名称空间中创建的。文件users.txt包含相关的用户详细信息,每行一个用户,格式为username=First Last<address@domain.com.au>,其中username是SVN日志中给定的用户名。(有关详细信息,请参见参考资料部分的第一个链接,特别是用户Casey的回答)。

版本

subversion 1.6.17(r1128011)git版本1.9.1GitLab版本7.2.1 ff1633fUbuntu服务器14.04

命令

git svn clone --stdlayout --no-metadata -A users.txt http://svn.domain.com.au/svn/repository/favourite-project
cd favourite-project
git remote add gitlab git@git.domain.com.au:dev-team/favourite-project.git
git push --set-upstream gitlab master

就是这样!在GitLab web UI中重新加载项目页面,您将看到现在列出的所有提交和文件。

笔记

如果有未知用户,git-svnclone命令将停止,在这种情况下,update-users.txt、cd-f收藏夹项目和git-svnfetch将从停止的位置继续。SVN存储库的标准主干标记分支布局是必需的。给git-svnclone命令的SVN URL在trunk/、tags/和branches/的正上方停止。git-svn-clone命令产生大量输出,包括顶部的一些警告;我无视警告。

将Subversion存储库干净地迁移到Git存储库。首先,您必须创建一个将Subversion提交作者名称映射到Git commiters的文件,比如~/authors.txt:

jmaddox = Jon Maddox <jon@gmail.com>
bigpappa = Brian Biggs <bigpappa@gmail.com>

然后您可以将Subversion数据下载到Git存储库中:

mkdir repo && cd repo
git svn init http://subversion/repo --no-metadata
git config svn.authorsfile ~/authors.txt
git svn fetch

如果您在Mac上,可以通过安装git-core+svn从MacPorts获取git-svn。

如果您的subversion存储库与所需的git存储库位于同一台机器上,那么您可以在init步骤中使用此语法,否则都一样:

git svn init file:///home/user/repoName --no-metadata

我们可以使用git-svnclone命令,如下所示。

svn log-q<svn_URL>|awk-F'|''/^r/{sub(“^”,“”,$2);sub(”$“,”,$2);print$2“=”$2“<”$2”>“}'|sort-u>authors.txt

上述命令将从SVN提交创建authors文件。

svn日志—复制时停止<svn_URL>

创建SVN项目时,上面的命令将为您提供第一个修订号。

git svn clone-r<svn_REV_NO>:HEAD--无最小化url--stdlayout--无元数据--作者文件authors.txt<svn_url>

以上命令将在本地创建Git存储库。

问题是它不会将分支和标签转换为推送。您必须手动执行这些操作。以下分支机构示例:

$ git remote add origin https://github.com/pankaj0323/JDProjects.git
$ git branch -a
* master
  remotes/origin/MyDevBranch
  remotes/origin/tags/MyDevBranch-1.0
  remotes/origin/trunk
$$ git checkout -b MyDevBranch origin/MyDevBranch
Branch MyDevBranch set up to track remote branch MyDevBranch from origin.
Switched to a new branch 'MyDevBranch'
$ git branch -a
* MyDevBranch
  master
  remotes/origin/MyDevBranch
  remotes/origin/tags/MyDevBranch-1.0
  remotes/origin/trunk
$

对于标记:

$git checkout origin/tags/MyDevBranch-1.0
Note: checking out 'origin/tags/MyDevBranch-1.0'.
You are in 'detached HEAD' state. You can look around, make experimental
changes and commit them, and you can discard any commits you make in this
state without impacting any branches by performing another checkout.

If you want to create a new branch to retain commits you create, you may
do so (now or later) by using -b with the checkout command again. Example:

  git checkout -b new_branch_name

HEAD is now at 3041d81... Creating a tag
$ git branch -a
* (detached from origin/tags/MyDevBranch-1.0)
  MyDevBranch
  master
  remotes/origin/MyDevBranch
  remotes/origin/tags/MyDevBranch-1.0
  remotes/origin/trunk
$ git tag -a MyDevBranch-1.0 -m "creating tag"
$git tag
MyDevBranch-1.0
$

现在将master、branches和标记推送到远程git存储库。

$ git push origin master MyDevBranch MyDevBranch-1.0
Counting objects: 14, done.
Delta compression using up to 8 threads.
Compressing objects: 100% (11/11), done.
Writing objects: 100% (14/14), 2.28 KiB | 0 bytes/s, done.
Total 14 (delta 3), reused 0 (delta 0)
To https://github.com/pankaj0323/JDProjects.git
 * [new branch]      master -> master
 * [new branch]      MyDevBranch -> MyDevBranch
 * [new tag]         MyDevBranch-1.0 -> MyDevBranch-1.0
$

svn2git实用程序

svn2git实用程序删除了带有分支和标记的手动工作。

使用命令sudogeminstallsvn2git安装它。之后运行以下命令。

$svn2git<SVN_URL>--authors.txt--修订版<SVN_REV_NO>

现在,您可以列出分支、标记并轻松推送它们。

$ git remote add origin https://github.com/pankaj0323/JDProjects.git
$ git branch -a
  MyDevBranch
* master
  remotes/svn/MyDevBranch
  remotes/svn/trunk
$ git tag
  MyDevBranch-1.0
$ git push origin master MyDevBranch MyDevBranch-1.0

假设您有20个分支和标记,显然svn2git将为您节省大量时间,这就是为什么我比原生命令更喜欢它的原因。这是一个很好的原生git-svnclone命令包装器。

有关完整的示例,请参阅我的博客条目。

实现这一目标有不同的方法。我尝试了其中的一些,发现在Windows操作系统上只安装了git和svn就可以了。

前提条件:

windows上的git(我用过这个)https://git-scm.com/ 安装了控制台工具的svn(我使用过乌龟svn)转储SVN存储库的文件。svnadmin转储/path/to/repository>repo_name.svn_dump

实现最终目标的步骤(将所有具有历史记录的存储库移动到git,首先是本地git,然后是远程git)

在REPO_NAME_FOLDER目录中创建空存储库(使用控制台工具或tortoiseSVN)cd REPO_NAME_PARENT_FOLDER,将dumpfile.dump放入REPO_NAME_PARENT_FOLDsvnadmin load REPO_NAME_FOLDER<dumpfile.dump等待此操作,可能需要很长时间此命令是无声的,因此打开第二个cmd窗口:svnserve-d-R--root REPO_NAME_FOLDER为什么不直接使用file:///...... ? 因为下一个命令将失败,无法打开。。。到URL:,感谢您的回答https://stackoverflow.com/a/6300968/4953065创建新文件夹SOURCE_GIT_foldercd源_GIT_FOLDERgit-svn克隆svn://localhost/等待此操作。

最后,我们得到了什么?

让我们查看本地存储库:

git log

看到您以前的提交吗?如果是-好

现在,您已经拥有了功能齐全的本地git存储库,其中包含您的源代码和旧svn历史记录。现在,如果要将其移动到某个服务器,请使用以下命令:

git remote add origin https://fullurlpathtoyourrepo/reponame.git
git push -u origin --all # pushes up the repo and its refs for the first time
git push -u origin --tags # pushes up any tags

在我的情况下,我不需要标签命令,因为我的repo没有标签。

祝你好运

我已经发布了一个将svn转换为git的分步指南(这里),包括将svn标记转换成git标记,将svn分支转换成git分支。

简短版本:

1) 从特定版本号克隆svn。(修订号必须是要移植的最旧版本)

git svn clone --username=yourSvnUsername -T trunk_subdir -t tags_subdir -b branches_subdir -r aRevisionNumber svn_url gitreponame

2) 获取svn数据。这一步是最耗时的一步。

cd gitreponame
git svn fetch

重复git-svn获取,直到无错误完成

3) 更新主分支

git svn rebase

4) 通过复制引用从svn分支创建本地分支

cp .git/refs/remotes/origin/* .git/refs/heads/

5) 将svn标记转换为git标记

git for-each-ref refs/remotes/origin/tags | sed 's#^.*\([[:xdigit:]]\{40\}\).*refs/remotes/origin/tags/\(.*\)$#\2 \1#g' | while read p; do git tag -m "tag from svn" $p; done

6) 将存储库放在更好的地方,如github

git remotes add newrepo git@github.com:aUser/aProjectName.git
git push newrepo refs/heads/*
git push --tags newrepo

如果你想了解更多细节,请阅读我的帖子或询问我。