Question

I have a repository which was created by copying files (not the history) from an SVN repository, with many changes added on top since.

I have since converted the history in SVN into git, and merged it with git merge -s ours.

The problem is when I do a git blame on a file, it still shows every line as being created by the initial commit in the git repository (which copied all the files from SVN), rather than the SVN commit which was really responsible.

Is there a way I can solve this without rewriting all of the git history?

Était-ce utile?

La solution

You can create a replacement ref for the initial commit from git to make it appear to most git commands that the history which originated in git was built upon history imported from svn.

With recent versions of git that can be done using the command:

git replace --graft <FIRST_GIT_COMMIT> <LATEST_SVN_COMMIT>

For older version which don't support that, you can do the same with the following commands:

git checkout -b temporary <FIRST_GIT_COMMIT>
# Set parent of next commit to last one from svn,
# but don't change the working tree or contents of next commit
git reset --soft <LATEST_SVN_COMMIT>
# Create a new commit using contents and message of the first git commit
git commit -C <FIRST_GIT_COMMIT>
# Tell git to use the newly created commit in place of the original git 
# commit in most cases.
git replace <FIRST_GIT_COMMIT> HEAD

But, in either case, replacement references do not get transferred automatically with the standard refspecs used for remotes either when pushing or pulling. Than can be done manually by using:

git push origin 'refs/replace/*:refs/replace/*'
git pull origin 'refs/replace/*:refs/replace/*'

It is not possible to have the altered history automatically transferred to other repositories without changing the commit ID of every commit which was originally created with git.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top