如何合并两个 Git 存储库?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1425892/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How do you merge two Git repositories?
提问by static_rtti
Consider the following scenario:
考虑以下场景:
I have developed a small experimental project A in its own Git repo. It has now matured, and I'd like A to be part of larger project B, which has its own big repository. I'd now like to add A as a subdirectory of B.
我在自己的 Git 存储库中开发了一个小型实验项目 A。它现在已经成熟,我希望 A 成为更大项目 B 的一部分,该项目拥有自己的大型存储库。我现在想将 A 添加为 B 的子目录。
How do I merge A into B, without losing history on any side?
如何将 A 合并到 B,而不会丢失任何一方的历史?
采纳答案by Simon Perepelitsa
A single branch of another repository can be easily placed under a subdirectory retaining its history. For example:
另一个存储库的单个分支可以轻松放置在保留其历史记录的子目录下。例如:
git subtree add --prefix=rails git://github.com/rails/rails.git master
This will appear as a single commit where all files of Rails master branch are added into "rails" directory. However the commit's title contains a reference to the old history tree:
这将显示为单个提交,其中 Rails 主分支的所有文件都添加到“rails”目录中。然而,提交的标题包含对旧历史树的引用:
Add 'rails/' from commit
<rev>
从提交中添加“rails/”
<rev>
Where <rev>
is a SHA-1 commit hash. You can still see the history, blame some changes.
<rev>
SHA-1 提交哈希在哪里。你仍然可以看到历史,怪一些变化。
git log <rev>
git blame <rev> -- README.md
Note that you can't see the directory prefix from here since this is an actual old branch left intact. You should treat this like a usual file move commit: you will need an extra jump when reaching it.
请注意,您无法从此处看到目录前缀,因为这是一个完整的实际旧分支。您应该将此视为通常的文件移动提交:到达它时需要额外的跳转。
# finishes with all files added at once commit
git log rails/README.md
# then continue from original tree
git log <rev> -- README.md
There are more complex solutions like doing this manually or rewriting the history as described in other answers.
有更复杂的解决方案,例如手动执行此操作或按照其他答案中的描述重写历史记录。
The git-subtree command is a part of official git-contrib, some packet managers install it by default (OS X Homebrew). But you might have to install it by yourself in addition to git.
git-subtree 命令是官方 git-contrib 的一部分,一些数据包管理器默认安装它(OS X Homebrew)。但是除了 git 之外,您可能还需要自己安装它。
回答by Andresch Serj
If you want to merge project-a
into project-b
:
如果你想合并project-a
到project-b
:
cd path/to/project-b
git remote add project-a path/to/project-a
git fetch project-a --tags
git merge --allow-unrelated-histories project-a/master # or whichever branch you want to merge
git remote remove project-a
Taken from: git merge different repositories?
摘自:git合并不同的存储库?
This method worked pretty well for me, it's shorter and in my opinion a lot cleaner.
这种方法对我来说效果很好,它更短,在我看来更干净。
In case you want to put project-a
into a subdirectory, you can use git-filter-repo
(filter-branch
is discouraged). Run the following commands before the commands above:
如果你想要把project-a
到子目录中,你可以使用git-filter-repo
(filter-branch
被劝阻)。在上述命令之前运行以下命令:
cd path/to/project-a
git filter-repo --to-subdirectory-filter project-a
An example of merging 2 big repositories, putting one of them into a subdirectory: https://gist.github.com/x-yuri/9890ab1079cf4357d6f269d073fd9731
合并 2 个大型存储库,将其中一个放入子目录的示例:https: //gist.github.com/x-yuri/9890ab1079cf4357d6f269d073fd9731
Note:The --allow-unrelated-histories
parameter only exists since git >= 2.9. See Git - git merge Documentation / --allow-unrelated-histories
注意:该--allow-unrelated-histories
参数只存在于 git >= 2.9 之后。参见Git - git merge 文档/--allow-unrelated-history
Update: Added --tags
as suggested by @jstadler in order to keep tags.
更新:--tags
按照@jstadler 的建议添加以保留标签。
回答by Jakub Nar?bski
Here are two possible solutions:
以下是两种可能的解决方案:
Submodules
子模块
Either copy repository A into a separate directory in larger project B, or (perhaps better) clone repository A into a subdirectory in project B. Then use git submoduleto make this repository a submoduleof a repository B.
要么将存储库 A 复制到较大项目 B 中的单独目录中,要么(也许更好)将存储库 A 克隆到项目 B 中的子目录中。然后使用git submodule使该存储库成为存储库 B的子模块。
This is a good solution for loosely-coupled repositories, where development in repository A continues, and the major portion of development is a separate stand-alone development in A. See also SubmoduleSupportand GitSubmoduleTutorialpages on Git Wiki.
这是松耦合的仓库,其中一个仓库继续发展一个很好的解决方案,以及发展的主要部分是又见一个单独的独立发展SubmoduleSupport和GitSubmoduleTutorial上的Git维基网页。
Subtree merge
子树合并
You can merge repository A into a subdirectory of a project B using the subtree mergestrategy. This is described in Subtree Merging and Youby Markus Prinz.
您可以使用子树合并策略将存储库 A 合并到项目 B 的子目录中。这在Markus Prinz 的Subtree Merging and You 中有描述。
git remote add -f Bproject /path/to/B
git merge -s ours --allow-unrelated-histories --no-commit Bproject/master
git read-tree --prefix=dir-B/ -u Bproject/master
git commit -m "Merge B project as our subdirectory"
git pull -s subtree Bproject master
(Option --allow-unrelated-histories
is needed for Git >= 2.9.0.)
(--allow-unrelated-histories
Git >= 2.9.0 需要选项。)
Or you can use git subtreetool (repository on GitHub) by apenwarr (Avery Pennarun), announced for example in his blog post A new alternative to Git submodules: git subtree.
或者您可以使用apenwarr (Avery Pennarun) 的git subtree工具(GitHub 上的存储库),例如在他的博客文章中宣布的Git 子模块的新替代方案: git subtree。
I think in your case (A is to be part of larger project B) the correct solution would be to use subtree merge.
我认为在您的情况下(A 将成为更大项目 B 的一部分)正确的解决方案是使用subtree merge。
回答by Greg Hewgill
The submodule approach is good if you want to maintain the project separately. However, if you really want to merge both projects into the same repository, then you have a bit more work to do.
如果您想单独维护项目,子模块方法很好。但是,如果您真的想将两个项目合并到同一个存储库中,那么您还有更多工作要做。
The first thing would be to use git filter-branch
to rewrite the names of everything in the second repository to be in the subdirectory where you would like them to end up. So instead of foo.c
, bar.html
, you would have projb/foo.c
and projb/bar.html
.
第一件事是使用git filter-branch
重写第二个存储库中所有内容的名称,使其位于您希望它们结束的子目录中。所以,而不是foo.c
, bar.html
,你会有projb/foo.c
和projb/bar.html
。
Then, you should be able to do something like the following:
然后,您应该能够执行以下操作:
git remote add projb [wherever]
git pull projb
The git pull
will do a git fetch
followed by a git merge
. There should be no conflicts, if the repository you're pulling to does not yet have a projb/
directory.
该git pull
会做一个git fetch
接着一个git merge
。如果您要拉到的存储库还没有projb/
目录,则应该没有冲突。
Further searching indicates that something similar was done to merge gitk
into git
. Junio C Hamano writes about it here: http://www.mail-archive.com/[email protected]/msg03395.html
进一步搜索表明已完成类似的操作以合并gitk
到git
. Junio C Hamano 在这里写到:http: //www.mail-archive.com/[email protected]/msg03395.html
回答by Paul Draper
git-subtree
is nice, but it is probably not the one you want.
git-subtree
很好,但它可能不是你想要的。
For example, if projectA
is the directory created in B, after git subtree
,
例如,如果projectA
是在B中创建的目录,之后git subtree
,
git log projectA
lists only onecommit: the merge. The commits from the merged project are for different paths, so they don't show up.
只列出一个提交:合并。合并项目的提交是针对不同路径的,因此它们不会显示。
Greg Hewgill's answer comes closest, although it doesn't actually say how to rewrite the paths.
Greg Hewgill 的回答最接近,尽管它实际上并没有说明如何重写路径。
The solution is surprisingly simple.
解决方案出奇的简单。
(1) In A,
(1) 在 A 中,
PREFIX=projectA #adjust this
git filter-branch --index-filter '
git ls-files -s |
sed "s,\t,&'"$PREFIX"'/," |
GIT_INDEX_FILE=$GIT_INDEX_FILE.new git update-index --index-info &&
mv $GIT_INDEX_FILE.new $GIT_INDEX_FILE
' HEAD
Note: This rewrites history, so if you intend to continue using this repo A, you may want to clone (copy) a throwaway copy of it first.
注意:这会重写历史记录,因此如果您打算继续使用此 repo A,您可能需要先克隆(复制)它的一次性副本。
Note Bene: You have to modify the substitute script inside the sed command in the case that you use non-ascii characters (or white characters) in file names or path. In that case the file location inside a record produced by "ls-files -s" begins with quotation mark.
注意:如果在文件名或路径中使用非 ASCII 字符(或白色字符),则必须修改 sed 命令中的替换脚本。在这种情况下,“ls-files -s”生成的记录内的文件位置以引号开头。
(2) Then in B, run
(2) 然后在 B 中,运行
git pull path/to/A
Voila! You have a projectA
directory in B. If you run git log projectA
, you will see all commits from A.
瞧!您projectA
在 B 中有一个目录。如果您运行git log projectA
,您将看到来自 A 的所有提交。
In my case, I wanted two subdirectories, projectA
and projectB
. In that case, I did step (1) to B as well.
就我而言,我想要两个子目录,projectA
以及projectB
. 在那种情况下,我也对 B 执行了步骤 (1)。
回答by Smar
If both repositories have same kind of files (like two Rails repositories for different projects), you can fetch data of the secondary repository to your current repository:
如果两个存储库具有相同类型的文件(例如不同项目的两个 Rails 存储库),您可以将辅助存储库的数据提取到当前存储库:
git fetch git://repository.url/repo.git master:branch_name
and then merge it to current repository:
然后将其合并到当前存储库:
git merge --allow-unrelated-histories branch_name
If your Git version is smaller than 2.9, remove --allow-unrelated-histories
.
如果您的 Git 版本小于 2.9,请删除--allow-unrelated-histories
.
After this, conflicts may occur. You can resolve them for example with git mergetool
. kdiff3
can be used solely with keyboard, so 5 conflict file takes when reading the code just few minutes.
在此之后,可能会发生冲突。例如,您可以使用git mergetool
. kdiff3
可以单独与键盘一起使用,因此在阅读代码时只需几分钟即可获得 5 个冲突文件。
Remember to finish the merge:
记得完成合并:
git commit
回答by Calahad
I kept losing history when using merge, so I ended up using rebase since in my case the two repositories are different enough not to end up merging at every commit:
我在使用合并时一直丢失历史记录,所以我最终使用了 rebase,因为在我的情况下,这两个存储库不同,不会在每次提交时都合并:
git clone git@gitorious/projA.git projA
git clone git@gitorious/projB.git projB
cd projB
git remote add projA ../projA/
git fetch projA
git rebase projA/master HEAD
=> resolve conflicts, then continue, as many times as needed...
=> 解决冲突,然后继续,根据需要多次...
git rebase --continue
Doing this leads to one project having all commits from projA followed by commits from projB
这样做会导致一个项目拥有来自 projA 的所有提交,然后是来自 projB 的提交
回答by Radon Rosborough
In my case, I had a my-plugin
repository and a main-project
repository, and I wanted to pretend that my-plugin
had always been developed in the plugins
subdirectory of main-project
.
就我而言,我有一个my-plugin
仓库和一个main-project
仓库,我想假装my-plugin
一直被发达plugins
的子目录main-project
。
Basically, I rewrote the history of the my-plugin
repository so that it appeared all development took place in the plugins/my-plugin
subdirectory. Then, I added the development history of my-plugin
into the main-project
history, and merged the two trees together. Since there was no plugins/my-plugin
directory already present in the main-project
repository, this was a trivial no-conflicts merge. The resulting repository contained all history from both original projects, and had two roots.
基本上,我重写了my-plugin
存储库的历史记录,以便所有开发都发生在plugins/my-plugin
子目录中。然后,我将 的发展历史添加my-plugin
到main-project
历史中,并将两棵树合并在一起。由于存储库中不存在plugins/my-plugin
目录main-project
,因此这是一个微不足道的无冲突合并。生成的存储库包含两个原始项目的所有历史记录,并且有两个根。
TL;DR
TL; 博士
$ cp -R my-plugin my-plugin-dirty
$ cd my-plugin-dirty
$ git filter-branch -f --tree-filter "zsh -c 'setopt extended_glob && setopt glob_dots && mkdir -p plugins/my-plugin && (mv ^(.git|plugins) plugins/my-plugin || true)'" -- --all
$ cd ../main-project
$ git checkout master
$ git remote add --fetch my-plugin ../my-plugin-dirty
$ git merge my-plugin/master --allow-unrelated-histories
$ cd ..
$ rm -rf my-plugin-dirty
Long version
长版
First, create a copy of the my-plugin
repository, because we're going to be rewriting the history of this repository.
首先,创建my-plugin
存储库的副本,因为我们将重写此存储库的历史记录。
Now, navigate to the root of the my-plugin
repository, check out your main branch (probably master
), and run the following command. Of course, you should substitute for my-plugin
and plugins
whatever your actual names are.
现在,导航到my-plugin
存储库的根目录,检查您的主分支(可能是master
),然后运行以下命令。当然,你应该替代my-plugin
和plugins
任何实际的名称。
$ git filter-branch -f --tree-filter "zsh -c 'setopt extended_glob && setopt glob_dots && mkdir -p plugins/my-plugin && (mv ^(.git|plugins) plugins/my-plugin || true)'" -- --all
Now for an explanation. git filter-branch --tree-filter (...) HEAD
runs the (...)
command on every commit that is reachable from HEAD
. Note that this operates directly on the data stored for each commit, so we don't have to worry about notions of "working directory", "index", "staging", and so on.
现在解释一下。git filter-branch --tree-filter (...) HEAD
在(...)
可从HEAD
. 请注意,这直接对为每个提交存储的数据进行操作,因此我们不必担心“工作目录”、“索引”、“暂存”等概念。
If you run a filter-branch
command that fails, it will leave behind some files in the .git
directory and the next time you try filter-branch
it will complain about this, unless you supply the -f
option to filter-branch
.
如果你运行一个filter-branch
失败的命令,它会在.git
目录中留下一些文件,下次你尝试时filter-branch
它会抱怨这个,除非你提供-f
选项filter-branch
。
As for the actual command, I didn't have much luck getting bash
to do what I wanted, so instead I use zsh -c
to make zsh
execute a command. First I set the extended_glob
option, which is what enables the ^(...)
syntax in the mv
command, as well as the glob_dots
option, which allows me to select dotfiles (such as .gitignore
) with a glob (^(...)
).
至于实际的命令,我没有太多运气bash
去做我想做的事情,所以我使用zsh -c
makezsh
执行命令。首先我设置extended_glob
选项,它是启用命令中的^(...)
语法mv
的glob_dots
选项,以及允许我选择.gitignore
带有 glob ( ^(...)
) 的点文件(例如)的选项。
Next, I use the mkdir -p
command to create both plugins
and plugins/my-plugin
at the same time.
接下来,我用mkdir -p
命令同时创建plugins
,并plugins/my-plugin
在同一时间。
Finally, I use the zsh
"negative glob" feature ^(.git|plugins)
to match all files in the root directory of the repository except for .git
and the newly created my-plugin
folder. (Excluding .git
might not be necessary here, but trying to move a directory into itself is an error.)
最后,我使用zsh
“negative glob”功能^(.git|plugins)
来匹配存储库根目录中除.git
新创建的my-plugin
文件夹之外的所有文件。(.git
此处可能不需要排除,但尝试将目录移动到自身中是错误的。)
In my repository, the initial commit did not include any files, so the mv
command returned an error on the initial commit (since nothing was available to move). Therefore, I added a || true
so that git filter-branch
would not abort.
在我的存储库中,初始提交不包含任何文件,因此该mv
命令在初始提交时返回了错误(因为没有可移动的内容)。因此,我添加了一个|| true
这样git filter-branch
就不会中止。
The --all
option tells filter-branch
to rewrite the history for allbranches in the repository, and the extra --
is necessary to tell git
to interpret it as a part of the option list for branches to rewrite, instead of as an option to filter-branch
itself.
该--all
选项告诉filter-branch
重写存储库中所有分支的历史记录,并且--
需要额外说明git
将其解释为要重写的分支的选项列表的一部分,而不是作为其filter-branch
自身的选项。
Now, navigate to your main-project
repository and check out whatever branch you want to merge into. Add your local copy of the my-plugin
repository (with its history modified) as a remote of main-project
with:
现在,导航到您的main-project
存储库并检查要合并到的任何分支。添加my-plugin
存储库的本地副本(修改其历史记录)作为远程main-project
:
$ git remote add --fetch my-plugin $PATH_TO_MY_PLUGIN_REPOSITORY
You will now have two unrelated trees in your commit history, which you can visualize nicely using:
您现在将在提交历史记录中有两个不相关的树,您可以使用以下方法很好地可视化:
$ git log --color --graph --decorate --all
To merge them, use:
要合并它们,请使用:
$ git merge my-plugin/master --allow-unrelated-histories
Note that in pre-2.9.0 Git, the --allow-unrelated-histories
option does not exist. If you are using one of these versions, just omit the option: the error message that --allow-unrelated-histories
prevents wasalso added in 2.9.0.
请注意,在 2.9.0 之前的 Git 中,该--allow-unrelated-histories
选项不存在。如果您正在使用这些版本之一,只需省略选项:--allow-unrelated-histories
阻止的错误消息也在2.9.0 中添加。
You should not have any merge conflicts. If you do, it probably means that either the filter-branch
command did not work correctly or there was already a plugins/my-plugin
directory in main-project
.
您不应该有任何合并冲突。如果你这样做,它可能意味着该filter-branch
命令没有正常工作或者已经有一个plugins/my-plugin
目录main-project
。
Make sure to enter an explanatory commit message for any future contributors wondering what hackery was going on to make a repository with two roots.
确保为任何未来的贡献者输入一个解释性的提交消息,他们想知道黑客正在做什么来创建一个具有两个根的存储库。
You can visualize the new commit graph, which should have two root commits, using the above git log
command. Note that only the master
branch will be merged. This means that if you have important work on other my-plugin
branches that you want to merge into the main-project
tree, you should refrain from deleting the my-plugin
remote until you have done these merges. If you don't, then the commits from those branches will still be in the main-project
repository, but some will be unreachable and susceptible to eventual garbage collection. (Also, you will have to refer to them by SHA, because deleting a remote removes its remote-tracking branches.)
你可以使用上面的git log
命令可视化新的提交图,它应该有两个根提交。请注意,只会master
合并分支。这意味着如果您my-plugin
要合并到main-project
树中的其他分支上有重要工作,则在my-plugin
完成这些合并之前,您应该避免删除远程。如果你不这样做,那么来自这些分支的提交仍将在main-project
存储库中,但有些将无法访问并且容易受到最终的垃圾收集。(此外,您必须通过 SHA 引用它们,因为删除远程会删除其远程跟踪分支。)
Optionally, after you have merged everything you want to keep from my-plugin
, you can remove the my-plugin
remote using:
或者,在合并了要保留的所有内容后my-plugin
,您可以my-plugin
使用以下方法删除遥控器:
$ git remote remove my-plugin
You can now safely delete the copy of the my-plugin
repository whose history you changed. In my case, I also added a deprecation notice to the real my-plugin
repository after the merge was complete and pushed.
您现在可以安全地删除my-plugin
您更改其历史记录的存储库副本。就我而言,我还在my-plugin
合并完成并推送后向真实存储库添加了弃用通知。
Tested on Mac OS X El Capitan with git --version 2.9.0
and zsh --version 5.2
. Your mileage may vary.
在 Mac OS X El Capitan 上使用git --version 2.9.0
和测试zsh --version 5.2
。你的旅费可能会改变。
References:
参考:
- https://git-scm.com/docs/git-filter-branch
- https://unix.stackexchange.com/questions/6393/how-do-you-move-all-files-including-hidden-from-one-directory-to-another
- http://www.refining-linux.org/archives/37/ZSH-Gem-2-Extended-globbing-and-expansion/
- Purging file from Git repo failed, unable to create new backup
- git, filter-branch on all branches
回答by Rian
I've been trying to do the same thing for days, I am using git 2.7.2. Subtree does not preserve the history.
几天来我一直在尝试做同样的事情,我正在使用 git 2.7.2。子树不保留历史记录。
You can use this method if you will not be using the old project again.
如果您不再使用旧项目,则可以使用此方法。
I would suggest that you branch B first and work in the branch.
我建议你先分支 B 并在分支中工作。
Here are the steps without branching:
以下是没有分支的步骤:
cd B
# You are going to merge A into B, so first move all of B's files into a sub dir
mkdir B
# Move all files to B, till there is nothing in the dir but .git and B
git mv <files> B
git add .
git commit -m "Moving content of project B in preparation for merge from A"
# Now merge A into B
git remote add -f A <A repo url>
git merge A/<branch>
mkdir A
# move all the files into subdir A, excluding .git
git mv <files> A
git commit -m "Moved A into subdir"
# Move B's files back to root
git mv B/* ./
rm -rf B
git commit -m "Reset B to original state"
git push
If you now log any of the files in subdir A you will get the full history
如果您现在记录 subdir A 中的任何文件,您将获得完整的历史记录
git log --follow A/<file>
This was the post that help me do this:
这是帮助我做到这一点的帖子:
回答by Finn Haakansson
If you want to put the files from a branch in repo B in a subtreeof repo A andalso preserve the history, keep reading. (In the example below, I am assuming that we want repo B's master branch merged into repo A's master branch.)
如果您想将 repo B 中分支中的文件放在 repo A 的子树中并保留历史记录,请继续阅读。(在下面的示例中,我假设我们希望 repo B 的 master 分支合并到 repo A 的 master 分支中。)
In repo A, first do the following to make repo B available:
在 repo A 中,首先执行以下操作以使 repo B 可用:
git remote add B ../B # Add repo B as a new remote.
git fetch B
Now we create a brand new branch (with only one commit) in repo A that we call new_b_root
. The resulting commit will have the files that were committed in the first commit of repo B's master branch but put in a subdirectory called path/to/b-files/
.
现在我们在 repo A 中创建一个全新的分支(只有一次提交),我们称之为new_b_root
。结果提交将包含在 repo B 的 master 分支的第一次提交中提交的文件,但放在名为path/to/b-files/
.
git checkout --orphan new_b_root master
git rm -rf . # Remove all files.
git cherry-pick -n `git rev-list --max-parents=0 B/master`
mkdir -p path/to/b-files
git mv README path/to/b-files/
git commit --date="$(git log --format='%ai' $(git rev-list --max-parents=0 B/master))"
Explanation: The --orphan
option to the checkout command checks out the files from A's master branch but doesn't create any commit. We could have selected any commit because next we clear out all the files anyway. Then, without committing yet (-n
), we cherry-pick the first commit from B's master branch. (The cherry-pick preserves the original commit message which a straight checkout doesn't seem to do.) Then we create the subtree where we want to put all files from repo B. We then have to move all files that were introduced in the cherry-pick to the subtree. In the example above, there's only a README
file to move. Then we commit our B-repo root commit, and, at the same time, we also preserve the timestamp of the original commit.
说明:--orphan
checkout 命令的选项从 A 的 master 分支检出文件,但不创建任何提交。我们可以选择任何提交,因为接下来我们无论如何都要清除所有文件。然后,在尚未提交 ( -n
) 的情况下,我们从 B 的主分支中挑选第一个提交。(cherry-pick 保留了原始提交消息,而直接结帐似乎没有这样做。)然后我们创建子树,我们要将所有来自 repo B 的文件放在其中。然后我们必须移动在樱桃采摘到子树。在上面的例子中,只有一个README
文件要移动。然后我们提交我们的 B-repo 根提交,同时,我们还保留原始提交的时间戳。
Now, we'll create a new B/master
branch on top of the newly created new_b_root
. We call the new branch b
:
现在,我们将B/master
在新创建的new_b_root
. 我们称新分支为b
:
git checkout -b b B/master
git rebase -s recursive -Xsubtree=path/to/b-files/ new_b_root
Now, we merge our b
branch into A/master
:
现在,我们将我们的b
分支合并到A/master
:
git checkout master
git merge --allow-unrelated-histories --no-commit b
git commit -m 'Merge repo B into repo A.'
Finally, you can remove the B
remote and temporary branches:
最后,您可以删除B
远程和临时分支:
git remote remove B
git branch -D new_b_root b
The final graph will have a structure like this:
最终的图形将具有如下结构: