将2个子目录的git合并到一个新创建的父目录中

ua4mk5z4  于 2023-02-07  发布在  Git
关注(0)|答案(1)|浏览(248)

我有一个具有以下结构的项目:

.
└── maindir
    ├── subdir1
    └── subdir2

我在subdir1subdir2中设置了一个git repo,开始了这个项目。项目变得越来越大,现在我不得不创建一个父目录maindir,并在其中创建一个git repo。然而现在看来,在subdir1subdir2中所做的更改并没有被maindir的git repo跟踪。此外,为了简单起见,我想把所有git repo的提交信息合并到一个git repo中,也就是maindir,我该怎么做?

    • 编辑1**

所以我试了一下评论中的链接(Git: Combining two independent repos to one without losing the history)的答案,得到了下面的输出,看起来比另一个SO问题更复杂,接下来我该怎么办?

$ git pull subdir1
remote: Enumerating objects: 58, done.
remote: Counting objects: 100% (58/58), done.
remote: Compressing objects: 100% (54/54), done.
remote: Total 58 (delta 25), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (58/58), 9.96 KiB | 231.00 KiB/s, done.
From standard_deviation
 * branch            HEAD       -> FETCH_HEAD
hint: Pulling without specifying how to reconcile divergent branches is
hint: discouraged. You can squelch this message by running one of the following
hint: commands sometime before your next pull:
hint:
hint:   git config pull.rebase false  # merge (the default strategy)
hint:   git config pull.rebase true   # rebase
hint:   git config pull.ff only       # fast-forward only
hint:
hint: You can replace "git config" with "git config --global" to set a default
hint: preference for all repositories. You can also pass --rebase, --no-rebase,
hint: or --ff-only on the command line to override the configured default per
hint: invocation.
fatal: refusing to merge unrelated histories
    • 编辑2**

我正在尝试git filter-repo软件包并尝试按照命令执行,但有一些细节我不明白。因此,我将其注解为"",以查看我是否正确理解了它

cd /path/to/subdir1 # now at level of subdir1
cd .. # now at level of maindir
mv subdir1 maindir # while at level of maindir, now renaming subdir1 to maindir, so there is maindir containing another maindir
git filter-repo --to-subdirectory-filter subdir1/ # using the package
cd ../subdir2 # This is what I do not understand: why the `..`? because we should still be at the level of the first maindir. What am I not getting right?
git filter-repo --to-subdirectory-filter subdir2/ # did not try from this point on
cd ../maindir # did not try
git remote add -f s2 ../subdir2 # did not try
git merge --allow-unrelated-histories s2/main # did not try
git remote remove s2 # did not try
z31licg0

z31licg01#

一种选择是将subdir1subdir2引用为maindir中的submodules

  • 将子目录仓库移到主目录 * 之外 *。
  • 将它们作为子模块添加回去:
cd /path/to/maindir
mv subdir1 ..
mv subdir2 ..
git rm --cached subdir1
git rm --cached subdir2
git commit -m "remove nested Git repositories"

git submodule add https://url/subdir1/remote/repository subdir1
git submodule add https://url/subdir2/remote/repository subdir2
git commit -m "Reference subdir1 and subdir2 repository inside maindir"
git push

注意:如果你从来没有在maindir中添加过嵌套的git仓库,就不需要git rm --cached,但是你仍然需要把它们移走。
这里假设子目录仓库已经被推送到了它们对应的远程仓库(在GitHub,GitLab,Bitbucket,...)
另一个选择是,为了避免“不相关的历史”,将一个subdir仓库转换为maindir,然后导入第二个。
这使用git filter-repo(需要为installed first)。
它使用路径快捷方式选项,遵循this gist

--to-subdirectory-filter <directory>

将项目根视为位于<directory>下。
等效于使用--path-rename :<directory>/
因此:

cd /path/to/subdir1
cd ..
mv subdir1 maindir
cd maindir
git filter-repo --to-subdirectory-filter subdir1/
cd ../subdir2
git filter-repo --to-subdirectory-filter subdir2/
cd ../maindir
git remote add -f s2 ../subdir2
git merge --allow-unrelated-histories s2/main
git remote remove s2

这一次:

  • 您不依赖于远程存储库(GitHub、GitLab、Bitbucket...)
  • 不使用子模块(对存储库的引用)
  • 这意味着你最终得到一个单独的git repo(而不是一个仓库引用两个其他仓库)

相关问题