You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用CMake编译MongoDB与Qt项目时出现链接错误求助

问题:Windows下CMake编译Qt+mongocxx项目链接报错

在Windows系统中,使用CMake编译集成vcpkg编译的mongocxx与Qt的项目时,链接阶段出现大量未定义引用错误。已尝试切换编译器(MinGW→MSVC)、替换库文件等操作,均未解决问题。

我的CMake配置

cmake_minimum_required(VERSION 3.5)

project(CmakeCBT VERSION 0.1 LANGUAGES CXX)

set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

include_directories("${CMAKE_CURRENT_LIST_DIR}/include")
include_directories("${CMAKE_CURRENT_LIST_DIR}/bin")
include_directories("${CMAKE_CURRENT_LIST_DIR}/lib")
include_directories("${CMAKE_CURRENT_LIST_DIR}/share")

find_package(QT NAMES Qt6 Qt5 REQUIRED COMPONENTS Widgets)
find_package(Qt${QT_VERSION_MAJOR} REQUIRED COMPONENTS Widgets)

set(libbsoncxx_DIR "${CMAKE_CURRENT_LIST_DIR}/share/libbsoncxx")
set(libmongocxx_DIR "${CMAKE_CURRENT_LIST_DIR}/share/libmongocxx")

find_package(libbsoncxx REQUIRED)
find_package(libmongocxx REQUIRED)

set(PROJECT_SOURCES
        main.cpp
        startwindow.cpp
        startwindow.h
        startwindow.ui
        studentwindow.cpp
        studentwindow.h
        studentwindow.ui
        dbcontroller.cpp
        dbcontroller.h
        errors.h
        errors.cpp
)

qt_add_executable(CmakeCBT
    MANUAL_FINALIZATION
    ${PROJECT_SOURCES}
)

target_link_libraries(CmakeCBT PUBLIC "${CMAKE_CURRENT_LIST_DIR}/lib/bsoncxx.lib")
target_link_libraries(CmakeCBT PUBLIC "${CMAKE_CURRENT_LIST_DIR}/lib/mongocxx.lib")
target_link_libraries(CmakeCBT PUBLIC "${CMAKE_CURRENT_LIST_DIR}/lib/bson-1.0.lib")
target_link_libraries(CmakeCBT PUBLIC "${CMAKE_CURRENT_LIST_DIR}/lib/mongoc-1.0.lib")
target_link_libraries(CmakeCBT PUBLIC "${CMAKE_CURRENT_LIST_DIR}/lib/zlib.lib")

target_link_libraries(CmakeCBT PRIVATE Qt${QT_VERSION_MAJOR}::Widgets)

if(${QT_VERSION} VERSION_LESS 6.1.0)
  set(BUNDLE_ID_OPTION MACOSX_BUNDLE_GUI_IDENTIFIER com.example.CmakeCBT)
endif()
set_target_properties(CmakeCBT PROPERTIES
    ${BUNDLE_ID_OPTION}
    MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
    MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
    MACOSX_BUNDLE TRUE
    WIN32_EXECUTABLE TRUE
)

include(GNUInstallDirs)
install(TARGETS CmakeCBT
    BUNDLE DESTINATION .
    LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
    RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)

if(QT_VERSION_MAJOR EQUAL 6)
    qt_finalize_executable(CmakeCBT)
endif()

错误日志

[1/5 3.3/sec] Automatic MOC and UIC for target CmakeCBT
[2/4 0.8/sec] Building CXX object CMakeFiles/CmakeCBT.dir/studentwindow.cpp.obj
[3/4 0.9/sec] Building CXX object CMakeFiles/CmakeCBT.dir/startwindow.cpp.obj
[4/4 1.1/sec] Linking CXX executable CmakeCBT.exe
FAILED: CmakeCBT.exe 
cmd.exe /C "cd . && C:\Qt\Tools\mingw1120_64\bin\g++.exe -DQT_QML_DEBUG -g -mwindows CMakeFiles/CmakeCBT.dir/CmakeCBT_autogen/mocs_compilation.cpp.obj CMakeFiles/CmakeCBT.dir/main.cpp.obj CMakeFiles/CmakeCBT.dir/startwindow.cpp.obj CMakeFiles/CmakeCBT.dir/studentwindow.cpp.obj CMakeFiles/CmakeCBT.dir/dbcontroller.cpp.obj CMakeFiles/CmakeCBT.dir/model.cpp.obj CMakeFiles/CmakeCBT.dir/errors.cpp.obj -o CmakeCBT.exe -Wl,--out-implib,libCmakeCBT.dll.a -Wl,--major-image-version,0,--minor-image-version,0  D:/Qt/CMAKESBT/CmakeCBT/lib/bsoncxx.lib  D:/Qt/CMAKESBT/CmakeCBT/lib/mongocxx.lib  D:/Qt/CMAKESBT/CmakeCBT/lib/bson-1.0.lib  D:/Qt/CMAKESBT/CmakeCBT/lib/mongoc-1.0.lib  D:/Qt/CMAKESBT/CmakeCBT/lib/zlib.lib  C:/Qt/6.6.0/mingw_64/lib/libQt6Widgets.a  C:/Qt/6.6.0/mingw_64/lib/libQt6Gui.a  C:/Qt/6.6.0/mingw_64/lib/libQt6Core.a  -lmpr  -luserenv  -lmingw32  C:/Qt/6.6.0/mingw_64/lib/libQt6EntryPoint.a  -lshell32  -ld3d11  -ldxgi  -ldxguid  -ld3d12  -lkernel32 -luser32 -lgdi32 -lwinspool -lshell32 -lole32 -loleaut32 -luuid -lcomdlg32 -ladvapi32 && cd ."
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: CMakeFiles/CmakeCBT.dir/dbcontroller.cpp.obj: in function `DBController::DBController()':
D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:3: undefined reference to `__imp__ZN8mongocxx7v_noabi8instanceC1Ev'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:7: undefined reference to `__imp__ZN8mongocxx7v_noabi8instanceC1Ev'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:7: undefined reference to `__imp__ZN8mongocxx7v_noabi8instanceaSEOS1_'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:7: undefined reference to `__imp__ZN8mongocxx7v_noabi8instanceD1Ev'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:8: undefined reference to `__imp__ZN8mongocxx7v_noabi3uriC1EN7bsoncxx7v_noabi6string13view_or_valueE'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:11: undefined reference to `__imp__ZN8mongocxx7v_noabi7options10server_apiC1ENS2_7versionE'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:12: undefined reference to `__imp__ZN8mongocxx7v_noabi7options6client15server_api_optsENS1_10server_apiE'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:14: undefined reference to `__imp__ZN8mongocxx7v_noabi6clientC1ERKNS0_3uriERKNS0_7options6clientE'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: D:/Qt/CMAKESBT/CmakeCBT/dbcontroller.cpp:14: undefined reference to `__imp__ZN8mongocxx7v_noabi6clientaSEOS1_'


D:/Qt/CMAKESBT/CmakeCBT/include/bsoncxx/builder/basic/sub_document.hpp:85: undefined reference to `__imp__ZN7bsoncxx7v_noabi7builder4core8key_viewESt17basic_string_viewIcSt11char_traitsIcEE'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: CMakeFiles/CmakeCBT.dir/dbcontroller.cpp.obj: in function `std::enable_if<(!std::is_convertible<int, std::function<void (bsoncxx::v_noabi::builder::basic::sub_document)> >::value)&&(!std::is_convertible<int, std::function<void (bsoncxx::v_noabi::builder::basic::sub_array)> >::value), void>::type bsoncxx::v_noabi::builder::basic::impl::generic_append<int>(bsoncxx::v_noabi::builder::core*, int&&)':
D:/Qt/CMAKESBT/CmakeCBT/include/bsoncxx/builder/basic/impl.hpp:55: undefined reference to `__imp__ZN7bsoncxx7v_noabi7builder4core6appendEi'
C:/Qt/Tools/mingw1120_64/bin/../lib/gcc/x86_64-w64-mingw32/11.2.0/../../../../x86_64-w64-mingw32/bin/ld.exe: CMakeFiles/CmakeCBT.dir/dbcontroller.cpp.obj:dbcontroller.c:(.rdata$.refptr._ZN12DBController10singleton_E[.refptr._ZN12DBController10singleton_E]+0x0): undefined reference to `DBController::singleton_'
collect2.exe: error: ld returned 1 exit status
ninja: build stopped: subcommand failed.

解决思路与方案

1. 确保库与编译器环境匹配

vcpkg编译mongocxx时,必须与当前项目使用的编译器完全一致:

  • 若用MinGW编译项目,vcpkg需指定对应的triplet,比如x64-mingw-static或x64-mingw-dynamic,重新编译mongocxx:
    vcpkg install mongocxx:x64-mingw-static
    
  • 切换编译器(如MSVC)时,必须同步用vcpkg针对MSVC的triplet(如x64-windows)重新编译mongocxx,不能混用不同编译器编译的库。

2. 正确使用find_package的目标链接

不要手动指定.lib文件路径,find_package会自动处理依赖关系和链接顺序。替换手动链接的代码:

# 替换原来的手动target_link_libraries行
target_link_libraries(CmakeCBT PRIVATE libbsoncxx::libbsoncxx libmongocxx::libmongocxx)

这会自动包含所有依赖库(如bson-1.0、mongoc-1.0、zlib等),无需手动添加。

3. 添加正确的预编译宏

根据mongocxx库的编译类型(静态/动态),添加对应的预编译宏:

  • 静态库:
    add_definitions(-DMONGOCXX_STATIC -DBSONCXX_STATIC)
    
  • 动态库:
    add_definitions(-DMONGOCXX_DYNAMIC -DBSONCXX_DYNAMIC)
    

vcpkg编译时默认的类型可通过triplet判断,-static结尾的是静态库,否则是动态库。

4. 修复DBController的静态成员定义

最后一个错误是DBController::singleton_未定义,需在dbcontroller.cpp中添加静态成员的定义:

DBController* DBController::singleton_ = nullptr;

确保头文件中声明的静态成员在cpp文件中有定义。

5. 清理CMake缓存后重新构建

修改CMake配置后,删除build目录下的所有文件,重新运行CMake生成构建文件,再执行编译,避免缓存导致的问题。


内容的提问来源于stack exchange,提问作者Никита Горчаков

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 04:19:52