自动重编译:如果一个CMake客户端项目依赖于一个单独的CMake库,如何让客户端项目重新构建它的依赖?

Automatic recompilation: if a CMake client project depends on a separate CMake library, how to have the client project re build its dependency?

随着代码库的增长,在不同的存储库之间组织它是有意义的,每个存储库都是一个单独的 CMake 管理的项目。

由于模块化,这通常意味着您最终会遇到 CMake 管理的项目 Application 依赖于另一个 CMake 管理的项目 Library,而两者都是内部代码(即由您的结构拥有和维护的代码)。

自动依赖重编译问题

然后,如果 Library 中的某些源代码被修改,则需要重新编译才能构建 Application。问题是:

是否可以让 "build Application" 命令(IDE 中的一个按钮,或在命令行上调用 make)首先重建 如果 文件已更改?

我建议使用 ExternalProject_Add 命令。

不同版本的文档略有不同:

如果您在获取正确的依赖项时遇到问题,this 线程可能会帮助您。

通过查看 OpenChemistry parent-project 是如何做到的,并得到 normanius 的回答的确认,事实证明这可以用相对较少的 CMake 脚本来实现代码。

事实证明,CMake CLI 提供了对目标构建系统的 "build" 操作的抽象。参见 --build option
ExternalProject_Add 可以看作是直接从 CMake 脚本使用此 CLI 界面的包装器。


假设有一个 CMake 管理的存储库,构建 libuseful,还有一个单独的 CMake 管理的存储库,构建 appawesome 具有依赖性在 libuseful.

find_package(libuseful CONFIG) # The usual way to find a dependency

# appawesome is the executable we are building, it depends on libuseful
add_executable(appawesome main.cpp)
target_link_libraries(appawesome libuseful)

添加自动重建

然后可以系统地构建 appawesome 首先尝试使用如下代码重建 libuseful

ExternalProject_Add(EP_libuseful)
    SOURCE_DIR <libuseful_sourcedir>  # containing libuseful's root CMakeLists.txt
    BINARY_DIR <libuseful_binarydir>  # containing libuseful's CMakeCache.txt
    BUILD_ALWAYS 1                    # Always rebuild libuseful
)

add_dependencies(libuseful EP_libuseful)

最后一行非常重要:find_package() 在配置模式下应该使 libuseful 导入目标可用。对 ExternalProject_Add 的调用使构建目标 EP_libuseful 可用(这是自定义构建步骤,构建 libuseful)。最后一行只是确保 libuseful 取决于它的构建步骤。