具有许多第三方依赖关系的大型跨平台C ++项目的磁盘上的物理布局

时间:2013-10-27 10:22:51

标签: c++ build cmake cross-platform organization

我正在重新组织使用CMake构建的具有许多第三方依赖关系的large cross-platform C++ project的物理(磁盘上)布局。

由于我们需要支持Windows,这是一个没有完善的软件包管理器的平台,我们很久以前就决定在源代码树中包含我们依赖的第三方库。但是,在我们支持的其他平台上,例如Linux和Mac OS X,许多这些第三方库都可以作为软件包提供,或者已经存在于系统中,很容易被CMake找到。

目前的项目布局如下:

root/
    src/
        3rd-party-lib1/       (build system modified to output to build/)
        3rd-party-lib2/       (build system modified to output to build/)
        project-module1/      (our own code)
        project-module2/      (our own code)
    build/                    (CMake is invoked from here)
        3rd-party-lib1-bin/
        3rd-party-lib2-bin/

第三方库已经过调整,因此在构建时,会将二进制文件输出到root/build/<lib>/

此布局的问题有多个:

  • 第三方库不再是100%原创。这使得更新它们比要求更困难。
  • src/目录包含我们自己的代码和第三方代码的混合,这令人困惑。
  • src/目录非常大。因为src/包含第三方库,所以与原始源代码的实际数量相比,它非常大,使备份我们自己的代码比所需的稍微复杂一些(我们不能只归档整个src/目录了)。
  • 项目存储库(Git)非常大,因为包含了第三方库(可能包含大量非源文件,如文档,测试数据等),以及每次更新时都会变大。不幸的是,除非我们决定使用新的存储库重新启动(不幸的是丢失了整个提交历史记录),否则无法回到这里。
  • 在Linux或Mac OS X上构建项目的用户根本不需要其中许多包含第三方库(例如zlib,libpng),尽管它们大大简化了Windows用户的工作。

另一种布局如下:

root/
    3rdparty/
        3rd-party-lib1/       (100% original, contains built artifacts)
        3rd-party-lib2/       (100% original, contains built artifacts)
    src/
        project-module1/      (our own code)
        project-module2/      (our own code)
    build/                    (CMake is invoked from here)

我们需要修改我们的CMake文件,以便在每个库的正确位置查找第三方头文件和库。

在本地跨平台项目中处理第三方库的最佳做法是什么?哪种布局会为我们的开发人员在各自的平台上带来最令人惊讶的构建体验?现有项目成功布局的具体例子也很受欢迎。

1 个答案:

答案 0 :(得分:7)

我的经验表明以下是最佳做法:

  • 当第三方开源库完全按原样使用时,在主git仓库中提交下载的压缩tarball的本地副本,以避免网络连接问题阻止软件构建。

  • 当第三方开源库几乎按原样使用时,需要进行调整(这个 在交叉编译时很常见:许多软件包需要对其配置步骤进行微调,存储压缩的tarball和统一的差异&#34;主git仓库中的补丁文件,并在ExternalProject_Add的PATCH_COMMAND步骤中应用补丁。

  • 当您的组织对(第三方)开源库进行大量修改或扩展时,请使用单独的git存储库来保存指向上游存储库的指针(当它也使用git时最简单,但是上游svn也可以管理)。将您的组织的更改提交到用于镜像上游的分支的不同分支。如果你愿意,你可以在主git repo和这个之间引入一个子模块关系,但是因为DOWNLOAD_COMMAND可以直接从任意git repo中获取,所以在技术上不需要这样做。

  • 通过在主git仓库中存档它们来处理单个目标平台的小型,不常见的第三方专有二进制文件是合理的。但是,可用于各种平台的第三方二进制文件很大,或者经常进化,应该存储在它们自己的git repo中,并通过DOWNLOAD_COMMAND获取,如上所述。