将旧的 git 历史记录添加到新存储库

Ste*_*art 6 git

我创建了一个 git 存储库并向其中提交了内容。

git clone git://newrepo.com/project.git # Empty repository
tar -xzvf project-0.6.tar.gz -C project     # Fill it with tar contents
cd project
git commit -a
... Do work
... Commit
... Push
Run Code Online (Sandbox Code Playgroud)

但后来发现了带有 git 历史记录的同一项目的恢复版本,是用早期版本的 tar.gz 制作的。

如何将旧项目的历史记录导入到新项目中?


我想我需要做这样的事情:

git clone git://newrepo.com/project.git                 # Start fresh
cp -r project project_backup                            # Backup the content
cd project                               
git init                                                # Wipe everything
git remote set-url origin git://oldrepo.com/project.git # Point to the old project
git pull                                                # Get clean history
cp -r ../project_backup .                               # Apply new content
git commit -a                                           # One big commit
git remote set-url origin git://newrepo.com/project.git # Point to the new project
git push                                                # Push changes
Run Code Online (Sandbox Code Playgroud)

但我不认为git init那样有效。man说它实际上并没有触及 git 历史记录。我听说git rebase可能是解决方案,但我不确定如何在这种情况下使用它。

以 git-manpage 格式:我会这样:

A---B---C master (oldrepo)

D---E---F master (newrepo)
Run Code Online (Sandbox Code Playgroud)

进入

A---B---C---D'---E'---F' master (newrepo)
Run Code Online (Sandbox Code Playgroud)

编辑:

确实可以推送访问oldrepo. 我确信我可以弄清楚如何将我的更改应用到oldrepo,但是那么我将如何替换newrepooldrepo

编辑2

git rebase被建议。我遇到了问题。当我解决冲突并完成变基时,

git clone git@newrepo.com/project.git project-rebase
cd project-rebase
git fetch --all
git remote add original https://oldrepo.com/project-old.git
git fetch original
git rebase --onto original/master 6210d0b3cf20f506ce0bab7849550b38c9effb15 master
--- resolving conflict ---
git rebase --continue
Run Code Online (Sandbox Code Playgroud)

此时我希望我们已经完成了。看起来git log很棒,但是:

$ git status
On branch master
Your branch and 'origin/master' have diverged,
and have 102 and 11 different commits each, respectively.
  (use "git pull" to merge the remote branch into yours)

nothing to commit, working tree clean'

$ git push origin master
To newrepo.com:project.git
 ! [rejected]        master -> master (non-fast-forward)
error: failed to push some refs to 'git@newrepo.com:project.git'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. Integrate the remote changes (e.g.
hint: 'git pull ...') before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.
Run Code Online (Sandbox Code Playgroud)

Sch*_*ern 8

是的,您应该能够使用git rebase它。

将旧存储库添加为遥控器并获取它。

git remote add original <directory or url>
git fetch original
Run Code Online (Sandbox Code Playgroud)

现在你已经像...

A - B - C [original/master]

D - E - F [master]
Run Code Online (Sandbox Code Playgroud)

然后在此基础上重新调整你的工作。您应该跳过添加 tarball 的新存储库中的第一次提交,D在此处提交,否则将恢复您的旧工作。

git rebase --onto original/master D master
Run Code Online (Sandbox Code Playgroud)

这将从但不包括 D、直至并包括 变基master。因此,只有 E 和 F 是源 tarball 顶部的补丁。

          E1 - F1 [master]
         /
A - B - C [original/master]
Run Code Online (Sandbox Code Playgroud)

可能会有冲突。


Ste*_*art 4

感谢施文的出色开局,问题得以解决。这是整个解决方案:

git clone git@newrepo.com:project.git
cd project
git fetch --all
git remote add original https://oldrepo.com/project-old.git
git fetch original
git rebase --onto original/master 6210d0b3cf20f506ce0bab7849550b38c9effb15 master

# Manual resolution of conflict

git rebase --continue
git push --force origin master      # Need to disable branch protection in gitlab
                                    # Re-enable protection in gitlab
Run Code Online (Sandbox Code Playgroud)

我缺少--force将整个远程分支替换为本地修改的分支。由于我的仓库位于 gitlab 中,因此 master 分支受到保护并且--force不允许。为了使该命令成功,我必须暂时取消对 master 的保护。

然后我继续每个分支:

git checkout --track origin/upstream
git rebase --onto original/upstream 6210d0b3cf20f506ce0bab7849550b38c9effb15    
# Manual resolution of conflict    
git rebase --continue
gir push --force origin upstream
Run Code Online (Sandbox Code Playgroud)

我的上一个分支没有冲突,所以这个很简单:

git checkout --track origin/pristine-tar
git rebase --onto original/pristine-tar 6210d0b3cf20f506ce0bab7849550b38c9effb15
git push --force origin pristine-tar
Run Code Online (Sandbox Code Playgroud)