git - 如何在不初始化子模块的情况下对所有子模块执行 `git pull`

标签 git git-submodules

给定一个包含数百个子模块的 git 存储库,我不需要或不想初始化这些子模块,因为这需要很长时间,我如何将子模块指针移动到每个子模块的最新提交?

如果所有子模块都已初始化,我可以使用类似 git submodule foreach git pull 的内容。

可能存在一些相关的问题,例如需要指定要 pull 每个子模块的哪个分支。在这种情况下,git 应该为每个子模块使用 .gitmodules 文件中指定的分支。我希望命令继续执行并遵循指定的分支,即使子模块的历史记录已被重写。如果 .gitmodules 文件中指定的分支不存在,我希望收到错误。

错误应该在命令输出的末尾报告或发送到日志文件,以便它们不会被忽略。

最佳答案

获取sha1远程上的分支而不克隆远程:使用 git ls-remote

git ls-remote <repourl> <branchname>

# example :
$ git ls-remote https://github.com/git/git master
f402ea68166bd77f09b176c96005ac7f8886e14b        refs/heads/master

要更新子模块的本地 sha1 而不克隆子模块:使用 git update-index

git update-index --cacheinfo 160000,<sha1>,full/path/to/submodule
  • 160000是一种特殊的文件模式,指示存储在此路径的对象是提交 ( link to docs )
  • full/path/to/submodule应该是从存储库根目录开始到子模块的完整路径
    例如:如果您的子模块存储在 foo/bar/baz 中,即使您当前的工作目录是 foo/bar ,您应该指定 foo/bar/baz作为路径

有关“更新子模块”部分的更多详细信息

据我所知,没有集成命令(例如:git submodule <something> 命令)可以执行此操作。

@torek 很好地解释了子模块 sha1 的存储位置 this answer :

The hash ID is embedded [...] in the tree object for whatever directory contains the submodule reference.

我知道直接更新的唯一方法是 git update-index命令。

错误检查

git ls-remote <remote> <branch> :

  • 如果您传递的分支名称不存在,此命令将不会输出任何内容;但它的退出代码将指示“成功”

git update-index --cacheinfo ... :

  • 此命令将检查您要更新的路径是否已存在
  • 它将检查 sha1 是否为 40 个字符的十六进制值
  • 但是,在更新 sha1 时不会检查其有效性(您手头没有存储库来检查提交是否存在...)

关于git - 如何在不初始化子模块的情况下对所有子模块执行 `git pull`,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62588847/

相关文章:

git - 追溯地将 Git 文件夹转换为子模块?

git 过滤器不是 'unmodifying' 文件

git - 子模块的文件未 check out

Git命令强制子模块中的特定提交

git - PS1 中的条件空间

docker - Git 2.8 无法更新子模块

javascript - Git 子模块、切换分支和包含外部 JS 依赖项的推荐方式(天哪)

Git diff 仅显示已修改的行

git clean -f -d 从我的本地目录中删除文件

git - Git 是否应该认为它从 pull 中获得的文件现在未被跟踪?