14

我在一个文件夹中有大量我克隆了很长一段时间的项目;最近我将整个文件夹移动到我的一个仓库中,并希望将这些克隆的项目转换为子模块,以便我将来可以更好地更新和控制。我在谷歌上搜索了很多关于如何做到这一点,但所有的教程都只讨论如何添加新的子模块。任何人都可以帮助我吗?

4

3 回答 3

13

将现有 git 存储库添加为子模块与添加新存储库相同。

  1. 首先将包含所有 git 存储库的文件夹设置为 git 存储库,并使用git init.
  2. 使用git submodule add https//example.com/remoterepo ./localrepo./localrepo您现有的 git 存储库在哪里。
    • 注意:您将获得remoterepofrom的 URL localrepo/.git/config
  3. 对要添加为子模块的所有现有存储库重复第二步。
  4. 现在您可以运行git submodule foreach git pull以更新所有子项目。

如果您有很多子模块,您可能需要编写一个小脚本来自动化第二步,这应该不难。

编辑

以下是我用来尝试重现评论中提到的错误的内容。我对命令进行了三次检查,但仍然看不到错误:

git --version

mkdir submoduletest
cd submoduletest

git init --bare remote_repo_A
git init --bare remote_repo_B 

git clone remote_repo_A local_repo_A
git clone remote_repo_B local_repo_B

cd local_repo_A
echo "test commit on repo B" >> test.txt
git add test.txt
git commit -m 'test commit message'
git push origin master

cd ../local_repo_B
echo "test commit on repo B" >> test.txt
git add test.txt
git commit -m 'test commit message'
git push origin master

cd ../local_repo_A
git clone ../remote_repo_B local_repo_B
git submodule add ../remote_repo_B ./local_repo_B
git submodule foreach git pull origin master

git add .
git ci -m 'we just added a submodule for remote_repo_B'

git submodule status

使用以下命令检查 的当前状态local_repo_A,它只有两个 blob 对象,一个用于“test.txt”,另一个用于隐式创建的“.gitmodules”文件,没有任何内容remote_repo_B添加到.local_repo_A

find .git/objects -type f | awk -F/ '{print $3$4}' | xargs -I {} git cat-file -t {} | grep blob

我回滚编辑的原因是因为编辑根本是错误的,它已经被另外两个调解人和我拒绝了,但后来其他人批准了它,我不确定这是 SO 的错误还是什么。但是编辑被拒绝了,即使是现在因为它完全错误,我已经在评论中解释了为什么,我没有冒犯任何人,但这浪费了我的时间,如果答案对你没有帮助,请投反对票。

同样,如果您没有改进它,请不要编辑我的答案。

于 2013-05-24T03:30:47.360 回答
6

为了添加许多子模块,我编写了这个简单的循环:

for repo in vim/bundle/*
do
  echo $repo
  pushd $repo
  url=$(git remote get-url $(git remote))
  echo $url
  popd
  git submodule add $url ./$repo
done

明显的限制我没有费心修复:

  • 不需要更改目录,很确定您可以将 git 目录作为参数传递给命令
  • git remote实际上返回所有遥控器,而不仅仅是当前,所以如果有多个,脚本会中断
于 2018-09-01T12:08:48.827 回答
5

我将添加到@neevek 的答案中,如果您收到already exists in the index错误,那么您可以尝试这个版本:

  1. 从缓存中删除每个“已经克隆的存储库” :(
    因为那里已经有一个对象不指向存储库作为子模块,并且必须首先从索引中删除它以防止冲突。您的存储库的内容或索引不会这样做时被删除)

    git rm --cached ./localrepo
    
  2. 使用git submodule add https//example.com/remoterepo ./localrepo./localrepo您现有的 git 存储库在哪里。

    • 注意:您将获得remoterepofrom的 URL localrepo/.git/config
  3. 对要添加为子模块的所有现有存储库重复第二步。
  4. 现在您可以运行git submodule foreach git pull以更新所有子项目。

如果您有很多子模块,您可能需要编写一个小脚本来自动化第二步。

于 2018-01-30T16:16:39.093 回答