包管理器与 Git Submodule/Subtree

Package Manager vs. Git Submodule/Subtree

是否有理由使用包管理器而不是 git submodules/subtrees,反之亦然? git 解决方案似乎比简单的包管理器麻烦得多。

假设 git 个子模块的 space 节省效益并不重要。

更新:有人为这个问题添加了一个 C++ 标签,但我已经删除了它。这个问题并不专门针对 C++。欢迎比已接受的答案更笼统的答案。

The git solutions seem to be a lot more hassle than a simple package manager.

这不是麻烦

这是关于构建项目的两种不同方式:

  1. 通过二进制依赖项,使用包管理器(Nexus, or Conan for C++:您声明您的依赖项,包管理器获取它们并在编译期间使用它们。
    这就是 pom.xml or a npm-package.json:您唯一的代码库中的另一个文件,它将指示编译器下载相关的依赖项
  2. 通过 source 依赖项,带有 Git 子模块或子树,您可以在其中存储对其他源代码的引用,导入它们,然后重新编译所有内容。
    例如,如果您的系统由一个前端 GUI 源代码和一个后端源代码组成,您可以在一个父项目存储库中引用这两个存储库,将它们的源代码组合到一个代码库中。

第一个在构建系统时很好,其中每个部分都有自己的发布生命周期,并且您想依赖预构建的依赖项。

当依赖项与主程序的链接更紧密时使用第二种。

或者当没有二进制依赖项时(例如 Go and its modules 就是这种情况)。

"If the technological context allows for packaging and formal dependency management, you should absolutely go this route."

以上内容来自 Mastering Git submodules,这是一篇写得很好且经过深思熟虑的文章,值得成为这个问题和许多类似 Whosebug 问题的最佳答案。

让我引用与这个问题相关的部分:

Are they the right tool for the job?

There are a number of situations where the physical presence of module code inside container code is mandated, usually because of the technology or framework being used. For instance, themes and plugins for Wordpress, Magento, etc. are often de facto installed by their mere presence at conventional locations inside the project tree, and this is the only way to “install” them.

In such a situation, going with submodules (or subtrees) probably is the right solution, provided you do need to version that code and collaborate around it with third parties (or deploy it on another machine); for strictly local, unversioned situations, symbolic links are probably enough, but this is not what this post is about.

On the other hand, if the technological context allows for packaging and formal dependency management, you should absolutely go this route instead: it lets you better split your codebase, avoid a number of side effects and pitfalls that litter the submodule space, and let you benefit from versioning schemes such as semantic versioning (semver) for your dependencies.