如何让FetchContent依赖的cpprestsdk在CMake配置阶段完成构建
解决方案
问题分析
核心问题在于FetchContent_MakeAvailable默认将依赖构建延迟到项目构建阶段,但配置阶段CMake需要解析cpprestsdk::cpprest目标,此时该目标尚未生成,导致报错。另外你额外添加的find_package属于冗余操作,OVERRIDE_FIND_PACKAGE已让find_package复用FetchContent的结果,无需重复调用。
修正步骤
- 移除冗余的
find_package调用:FetchContent_MakeAvailable已负责导入cpprestsdk的CMake目标,无需额外执行find_package。 - 强制依赖在配置阶段完成构建:通过手动触发CMake的配置与构建命令,在项目配置阶段就完成cpprestsdk的编译,确保目标在配置阶段就存在。
修正后的CMakeLists.txt
cmake_minimum_required(VERSION 3.5) project(myproject) include(FetchContent) # 关闭cpprestsdk的WERROR选项 set(ENABLE_WERROR OFF CACHE BOOL "Turn off Treat warnings as errors" FORCE) set(WERROR OFF CACHE BOOL "Turn off Treat warnings as errors" FORCE) FetchContent_Declare( cpprestsdk GIT_REPOSITORY https://github.com/microsoft/cpprestsdk.git GIT_TAG v2.10.17 OVERRIDE_FIND_PACKAGE ) # 检查cpprestsdk是否已被填充 FetchContent_GetProperties(cpprestsdk) if(NOT cpprestsdk_POPULATED) # 填充依赖(下载、检出源码) FetchContent_Populate(cpprestsdk) # 在配置阶段手动构建cpprestsdk set(cpprest_build_dir "${cpprestsdk_BINARY_DIR}") file(MAKE_DIRECTORY "${cpprest_build_dir}") # 执行cmake配置 execute_process( COMMAND ${CMAKE_COMMAND} -S "${cpprestsdk_SOURCE_DIR}" -B "${cpprest_build_dir}" -DENABLE_WERROR=OFF -DWERROR=OFF -DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE} -DCMAKE_C_COMPILER=${CMAKE_C_COMPILER} -DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER} RESULT_VARIABLE cpprest_config_result OUTPUT_VARIABLE cpprest_config_output ERROR_VARIABLE cpprest_config_error ) if(NOT cpprest_config_result EQUAL 0) message(FATAL_ERROR "Failed to configure cpprestsdk:\n${cpprest_config_error}") endif() # 执行cmake构建 execute_process( COMMAND ${CMAKE_COMMAND} --build "${cpprest_build_dir}" --config ${CMAKE_BUILD_TYPE} RESULT_VARIABLE cpprest_build_result OUTPUT_VARIABLE cpprest_build_output ERROR_VARIABLE cpprest_build_error ) if(NOT cpprest_build_result EQUAL 0) message(FATAL_ERROR "Failed to build cpprestsdk:\n${cpprest_build_error}") endif() # 导入cpprestsdk的目标 add_subdirectory("${cpprestsdk_SOURCE_DIR}" "${cpprest_build_dir}" EXCLUDE_FROM_ALL) endif() add_executable(myproject svr.cc) target_link_libraries(myproject cpprestsdk::cpprest )
关键说明
- 手动调用
execute_process执行CMake配置和构建命令,强制在项目配置阶段完成cpprestsdk的编译,确保cpprestsdk::cpprest目标在配置阶段已生成。 - 通过
FetchContent_GetProperties和NOT cpprestsdk_POPULATED判断依赖是否已处理,避免重复执行构建步骤。 - 传递当前项目的编译器、构建类型等参数给cpprestsdk的构建,保证构建环境一致。
内容的提问来源于stack exchange,提问作者Michaelzh
相关产品推荐
相关产品推荐

