วิธีเริ่มทำงานกับ GTest และ CMake


125

ฉันเพิ่งถูกขายโดยใช้ CMake สำหรับการรวบรวมโปรเจ็กต์ C ++ ของฉันและตอนนี้ต้องการเริ่มเขียนการทดสอบหน่วยสำหรับรหัสของฉัน ฉันตัดสินใจที่จะใช้ยูทิลิตี้ Google Test เพื่อช่วยในเรื่องนี้ แต่ต้องการความช่วยเหลือในการเริ่มต้นใช้งาน

ทุกวันผมได้อ่านคำแนะนำต่างๆและตัวอย่าง ได้แก่รองพื้นการแนะนำที่ IBMและคำถามบางอย่างเกี่ยวกับ SO ( ที่นี่และที่นี่ ) เช่นเดียวกับแหล่งข้อมูลอื่น ๆ ที่ฉันติดตามของหาย ฉันรู้ว่ามีอะไรมากมายที่นั่น แต่ฉันก็ยังคงประสบปัญหา

ขณะนี้ฉันกำลังพยายามใช้การทดสอบขั้นพื้นฐานที่สุดเพื่อยืนยันว่าฉันได้รวบรวม / ติดตั้ง gtest ถูกต้องแล้วและไม่ได้ผล ไฟล์ต้นฉบับเดียว (testgtest.cpp) ถูกนำมาจากคำตอบก่อนหน้านี้เกือบทั้งหมด:

#include <iostream>

#include "gtest/gtest.h"

TEST(sample_test_case, sample_test)
{
    EXPECT_EQ(1, 1);
}

และ CMakeLists.txt ที่เกี่ยวข้องของฉันมีดังนี้:

cmake_minimum_required(VERSION 2.6)
project(basic_test)

# Setup testing
enable_testing()
find_package(GTest REQUIRED)
include_directories(${GTEST_INCLUDE_DIR})

# Add test cpp file
add_executable(runUnitTests
    testgtest.cpp
)

# Link test executable against gtest & gtest_main
target_link_libraries(runUnitTests ${GTEST_LIBRARY_DEBUG} ${GTEST_MAIN_LIBRARY_DEBUG})

add_test(
    NAME runUnitTests
    COMMAND runUnitTests
)

โปรดทราบว่าฉันเลือกที่จะเชื่อมโยงกับ gtest_main แทนที่จะระบุ main ที่ท้ายไฟล์ cpp เนื่องจากฉันเชื่อว่าสิ่งนี้จะช่วยให้สามารถปรับขนาดการทดสอบไปยังไฟล์หลาย ๆ ไฟล์ได้ง่ายขึ้น

เมื่อสร้างไฟล์. sln ที่สร้างขึ้น (ใน Visual C ++ 2010 Express) ฉันได้รับรายการข้อผิดพลาดจำนวนมากของแบบฟอร์ม

2>msvcprtd.lib(MSVCP100D.dll) : error LNK2005: "public: virtual __thiscall std::basic_iostream<char,struct std::char_traits<char> >::~basic_iostream<char,struct std::char_traits<char> >(void)" (??1?$basic_iostream@DU?$char_traits@D@std@@@std@@UAE@XZ) already defined in gtestd.lib(gtest-all.obj)

ซึ่งฉันคิดว่าฉันเชื่อมโยงกับไลบรารี gtest ไม่สำเร็จ ฉันได้ตรวจสอบให้แน่ใจว่าเมื่อเชื่อมโยงกับไลบรารีดีบักฉันได้พยายามสร้างในโหมดดีบักแล้ว

แก้ไข

หลังจากทำการขุดค้นเพิ่มเติมแล้วฉันคิดว่าปัญหาของฉันเกี่ยวข้องกับประเภทของไลบรารีที่ฉันกำลังสร้างขึ้น เมื่อสร้าง gtest ด้วย CMake หากBUILD_SHARED_LIBSไม่มีการตรวจสอบและฉันเชื่อมโยงโปรแกรมกับไฟล์. lib เหล่านี้ฉันได้รับข้อผิดพลาดที่กล่าวถึงข้างต้น อย่างไรก็ตามหากBUILD_SHARED_LIBSตรวจสอบแล้วฉันจะสร้างชุดของไฟล์. lib และ. dll เมื่อตอนนี้เชื่อมโยงกับไฟล์. lib เหล่านี้โปรแกรมจะคอมไพล์ แต่เมื่อรันบ่นว่าไม่พบ gtest.dll

ความแตกต่างระหว่าง a SHAREDและ not SHAREDlibrary คืออะไรและถ้าฉันเลือกไม่แชร์ทำไมมันถึงใช้ไม่ได้ มีตัวเลือกใน CMakeLists.txt สำหรับโครงการของฉันที่ฉันหายไปหรือไม่?


4
คุณสามารถหลีกเลี่ยงรวมถึงแหล่ง GTest ในของคุณเองโดยใช้มากกว่าExternalProject_Add add_subdirectoryดูรายละเอียดคำตอบนี้
Fraser

เหตุใดเราจึงมีสิทธิ์เข้าถึง $ {gtest_SOURCE_DIR} ในตัวอย่างโซลูชันด้านบน ตัวแปรนั้นประกาศอย่างไร / ที่ไหน
dmonopoly

มันประกาศใน gtest-1.6.0 / CMakeLists.txt: "project (gtest CXX C)" ซึ่งทำให้ตัวแปร gtest_SOURCE_DIR และ gtest_BINARY_DIR พร้อมใช้งาน
dmonopoly

1
อะไรenable_testing()ทำอย่างไร
updogliu

1
@updogliu: เปิดใช้งาน ctest และเป้าหมาย 'test' (หรือ 'RUN_TESTS') มันเล่นร่วมกับคำสั่ง add_test () cmake
Ela782

คำตอบ:


76

โซลูชันนี้เกี่ยวข้องกับการวางไดเร็กทอรีต้นทาง gtest เป็นไดเร็กทอรีย่อยของโปรเจ็กต์ของคุณ ฉันได้รวม CMakeLists.txt ที่ใช้งานได้ไว้ด้านล่างหากเป็นประโยชน์กับทุกคน

cmake_minimum_required(VERSION 2.6)
project(basic_test)

################################
# GTest
################################
ADD_SUBDIRECTORY (gtest-1.6.0)
enable_testing()
include_directories(${gtest_SOURCE_DIR}/include ${gtest_SOURCE_DIR})

################################
# Unit Tests
################################
# Add test cpp file
add_executable( runUnitTests testgtest.cpp )
# Link test executable against gtest & gtest_main
target_link_libraries(runUnitTests gtest gtest_main)
add_test( runUnitTests runUnitTests )

3
ฉันไม่แน่ใจว่า add_test () ทำอะไร แต่ดูเหมือนจะไม่ส่งผลให้ไบนารีทดสอบทำงาน ... ฉันขาดอะไรไปหรือเปล่า?
weberc2

4
ไม่ใช่เพื่อเอาชนะม้าตาย แต่ฉันคิดว่าสิ่งนี้ควรค่าแก่การกล่าวถึงอีกครั้ง ความคิดเห็นของ Fraser ด้านบนให้ความสำคัญอย่างยิ่ง: "คุณสามารถหลีกเลี่ยงการรวมแหล่งที่มาของ GTest ด้วยตัวคุณเองโดยใช้ ExternalProject_Add แทน add_subdirectory" ดูคำตอบและความคิดเห็นของ Fraser สำหรับรายละเอียดที่นี่: stackoverflow.com/a/9695234/1735836
Patricia

1
ในกรณีของฉันฉันต้องเพิ่มpthreadไปยังไลบรารีที่เชื่อมโยงโดยเปลี่ยนบรรทัดสุดท้ายที่สองเป็นtarget_link_libraries(runUnitTests gtest gtest_main pthread)
panmari

3
@ weberc2 คุณต้องรันmake testเพื่อรันการทดสอบหรือเรียกใช้ctestจากไดเร็กทอรีบิลด์ เรียกใช้ctest -Vเพื่อดูผลลัพธ์การทดสอบของ Google รวมทั้งctestผลลัพธ์
Patrick

38

นี่คือตัวอย่างการทำงานที่สมบูรณ์ที่ฉันเพิ่งทดสอบ ดาวน์โหลดโดยตรงจากเว็บไม่ว่าจะเป็น tarball คงที่หรือไดเรกทอรีการโค่นล้มล่าสุด

cmake_minimum_required (VERSION 3.1)

project (registerer)

##################################
# Download and install GoogleTest

include(ExternalProject)
ExternalProject_Add(gtest
  URL https://googletest.googlecode.com/files/gtest-1.7.0.zip
  # Comment above line, and uncomment line below to use subversion.
  # SVN_REPOSITORY http://googletest.googlecode.com/svn/trunk/ 
  # Uncomment line below to freeze a revision (here the one for 1.7.0)
  # SVN_REVISION -r700

  PREFIX ${CMAKE_CURRENT_BINARY_DIR}/gtest
  INSTALL_COMMAND ""
)
ExternalProject_Get_Property(gtest source_dir binary_dir)

################
# Define a test
add_executable(registerer_test registerer_test.cc)

######################################
# Configure the test to use GoogleTest
#
# If used often, could be made a macro.

add_dependencies(registerer_test gtest)
include_directories(${source_dir}/include)
target_link_libraries(registerer_test ${binary_dir}/libgtest.a)
target_link_libraries(registerer_test ${binary_dir}/libgtest_main.a)

##################################
# Just make the test runnable with
#   $ make test

enable_testing()
add_test(NAME    registerer_test 
         COMMAND registerer_test)

7
ฉันไม่รู้ว่าทำไมคุณถึงถูกโหวตให้เรื่องนี้ โซลูชันของคุณป้องกันไม่ให้ใครบางคนตรวจสอบใน Google Test เพื่อควบคุมเวอร์ชัน ความรุ่งโรจน์สำหรับการแก้ปัญหาของคุณ
Sal

4
ตอนนี้ URL ที่คุณใช้เสีย URL ที่เป็นปัจจุบันคือhttps://github.com/google/googletest/archive/release-1.8.0.zip
oscfri

คำตอบที่ดี ควรเป็นหมายเลข 1
Mr00Anderson

1
คำตอบโลภ! นอกจากนี้เรายังสามารถใช้GIT_REPOSITORY https://github.com/google/googletest.git GIT_TAG release-1.8.1แทน URL ได้
TingQian LI

URL ไปยังรุ่นล่าสุด gtest คือ:https://github.com/google/googletest/archive/release-1.10.0.zip
vahancho

16

คุณจะได้รับสิ่งที่ดีที่สุดจากทั้งสองโลก เป็นไปได้ที่จะใช้ExternalProjectเพื่อดาวน์โหลดซอร์ส gtest จากนั้นใช้add_subdirectory()เพื่อเพิ่มลงในบิลด์ของคุณ สิ่งนี้มีข้อดีดังต่อไปนี้:

  • gtest ถูกสร้างขึ้นเป็นส่วนหนึ่งของบิลด์หลักของคุณดังนั้นจึงใช้แฟล็กคอมไพเลอร์เดียวกันเป็นต้นและด้วยเหตุนี้จึงหลีกเลี่ยงปัญหาเช่นเดียวกับที่อธิบายไว้ในคำถาม
  • ไม่จำเป็นต้องเพิ่มแหล่งที่มาที่ละเอียดที่สุดให้กับแผนผังแหล่งที่มาของคุณ

ใช้ในลักษณะปกติ ExternalProject จะไม่ทำการดาวน์โหลดและคลายไฟล์ในเวลากำหนดค่า (เช่นเมื่อเรียกใช้ CMake) แต่คุณสามารถทำได้ด้วยการทำงานเพียงเล็กน้อย ฉันได้เขียนบล็อกโพสต์เกี่ยวกับวิธีการทำสิ่งนี้ซึ่งรวมถึงการใช้งานทั่วไปซึ่งใช้ได้กับโครงการภายนอกใด ๆ ที่ใช้ CMake เป็นระบบสร้างไม่ใช่แค่ gtest คุณสามารถค้นหาได้ที่นี่:

อัปเดต: ขณะนี้แนวทางนี้เป็นส่วนหนึ่งของเอกสาร googletestด้วย


2
IMO นี่อาจเป็นวิธีที่สะอาดที่สุดในการใช้การทดสอบของ Google กับโครงการ CMake ฉันหวังว่าผู้ดูแลจะให้ความสำคัญกับเนื้อหาและคุณภาพของคำตอบ
NameRakes

โมดูลทั่วไป DownloadProject.cmake ที่เชื่อมโยงนั้นยอดเยี่ยมมาก รู้สึกเหมือนพื้นฐานสำหรับ cmake ที่มีระบบการจัดการแพ็คเกจซึ่งสิ่งที่ฉันต้องการคือรายการลิงก์ไปยัง URL github ที่เข้ากันได้กับ CMake
Josh Peak

13

เป็นไปได้มากว่าความแตกต่างของตัวเลือกคอมไพเลอร์ระหว่างไบนารีทดสอบของคุณกับไลบรารีทดสอบของ Google คือการตำหนิข้อผิดพลาดดังกล่าว นั่นเป็นเหตุผลที่แนะนำให้นำการทดสอบ Google ในแบบฟอร์มต้นทางมาและสร้างพร้อมกับการทดสอบของคุณ ง่ายมากที่จะทำใน CMake คุณเพียงแค่เรียกใช้ ADD_SUBDIRECTORYด้วยพา ธ ไปยังรูท gtest จากนั้นคุณสามารถใช้เป้าหมายห้องสมุดสาธารณะ ( gtestและgtest_main) ที่กำหนดไว้ที่นั่น มีข้อมูลพื้นฐานเพิ่มเติมในเธรด CMakeนี้ในกลุ่ม googletestframework

[แก้ไข] BUILD_SHARED_LIBSตัวเลือกนี้มีผลเฉพาะบน Windows ในตอนนี้ ระบุประเภทของไลบรารีที่คุณต้องการให้ CMake สร้าง หากคุณตั้งค่าเป็นONCMake จะสร้างไฟล์เหล่านั้นเป็น DLL ซึ่งต่างจาก libs แบบคงที่ ในกรณีนี้คุณต้องสร้างการทดสอบของคุณด้วย -DGTEST_LINKED_AS_SHARED_LIBRARY = 1 และคัดลอกไฟล์ DLL ที่สร้างโดย CMake ไปยังไดเร็กทอรีด้วยไบนารีทดสอบของคุณ (CMake จะวางไว้ในไดเร็กทอรีเอาต์พุตแยกต่างหากโดยค่าเริ่มต้น) เว้นแต่ gtest ใน static lib จะไม่ได้ผลสำหรับคุณการตั้งค่าตัวเลือกนั้นจะไม่ง่ายกว่า


1
ขอบคุณมากไม่ทราบว่าคุณสามารถสร้างโครงการแยกจาก CMakeLists เดียวกันได้อย่างนั้น ตอนนี้ฉันสามารถพูดได้อย่างปลอดภัยว่า EXPECT_EQ (1.0 == 1.0) ผ่านและ EXPECT_EQ (0.0 == 1.0) ล้มเหลว ตอนนี้ถึงเวลาสำหรับการทดสอบจริงเพิ่มเติม ...
คริส

2

หลังจากทำการขุดค้นเพิ่มเติมแล้วฉันคิดว่าปัญหาของฉันเกี่ยวข้องกับประเภทของไลบรารีที่ฉันกำลังสร้างขึ้น เมื่อสร้าง gtest ด้วย CMake หากยกเลิกการเลือก BUILD_SHARED_LIBS และฉันเชื่อมโยงโปรแกรมกับไฟล์. lib เหล่านี้ฉันได้รับข้อผิดพลาดที่กล่าวถึงข้างต้น อย่างไรก็ตามหาก BUILD_SHARED_LIBS ถูกตรวจสอบฉันจะสร้างชุดของไฟล์. lib และ. dll เมื่อตอนนี้เชื่อมโยงกับไฟล์. lib เหล่านี้โปรแกรมจะคอมไพล์ แต่เมื่อรันบ่นว่าไม่พบ gtest.dll

นั่นเป็นเพราะคุณต้องเพิ่ม -DGTEST_LINKED_AS_SHARED_LIBRARY = 1 ลงในนิยามคอมไพเลอร์ในโปรเจ็กต์ของคุณหากคุณต้องการใช้ gtest เป็นไลบรารีที่แชร์

คุณยังสามารถใช้ไลบรารีแบบคงที่ได้หากคุณคอมไพล์ด้วยตัวเลือก gtest_force_shared_crt เพื่อกำจัดข้อผิดพลาดที่คุณเห็น

ฉันชอบห้องสมุด แต่การเพิ่มเข้าไปในโครงการเป็นความเจ็บปวดจริงๆ และคุณไม่มีโอกาสที่จะทำอย่างถูกต้องเว้นแต่คุณจะขุด (และแฮ็ก) ลงในไฟล์ gtest cmake ความอัปยศ. โดยเฉพาะอย่างยิ่งฉันไม่ชอบแนวคิดในการเพิ่ม gtest เป็นแหล่งที่มา :)


1

OP ใช้ Windows และวิธีที่ง่ายกว่ามากในการใช้ GTest ในปัจจุบันคือvcpkg + cmake


ติดตั้ง vcpkg ตามhttps://github.com/microsoft/vcpkgและตรวจสอบให้แน่ใจว่าคุณสามารถเรียกใช้vcpkgจากบรรทัด cmd จดโฟลเดอร์การติดตั้ง vcpkg เช่น C:\bin\programs\vcpkg.

ติดตั้ง gtest โดยใช้vcpkg install gtest: สิ่งนี้จะดาวน์โหลดรวบรวมและติดตั้ง GTest

ใช้ CmakeLists.txt ด้านล่าง: โปรดทราบว่าเราสามารถใช้เป้าหมายแทนการรวมโฟลเดอร์ได้

cmake_minimum_required(VERSION 3.15)
project(sample CXX)
enable_testing()
find_package(GTest REQUIRED)
add_executable(test1 test.cpp source.cpp)
target_link_libraries(test1 GTest::GTest GTest::Main)
add_test(test-1 test1)

เรียกใช้ cmake ด้วย: (แก้ไขโฟลเดอร์ vcpkg หากจำเป็นและตรวจสอบให้แน่ใจว่าพา ธ ไปยังไฟล์ vcpkg.cmake toolchain ถูกต้อง)

cmake -B build -DCMAKE_TOOLCHAIN_FILE=C:\bin\programs\vcpkg\scripts\buildsystems\vcpkg.cmake

และสร้างโดยใช้cmake --build buildตามปกติ โปรดทราบว่า vcpkg จะคัดลอก gtest (d) .dll / gtest (d) _main.dll ที่ต้องการจากโฟลเดอร์การติดตั้งไปยังโฟลเดอร์ Debug / Release

ทดสอบด้วยcd build & ctest.


0

โซลูชันของคุณและ VladLosevs น่าจะดีกว่าของฉัน อย่างไรก็ตามหากคุณต้องการวิธีแก้ปัญหาแบบเดรัจฉานลองทำดังนี้:

SET(CMAKE_EXE_LINKER_FLAGS /NODEFAULTLIB:\"msvcprtd.lib;MSVCRTD.lib\")

FOREACH(flag_var
    CMAKE_CXX_FLAGS CMAKE_CXX_FLAGS_DEBUG CMAKE_CXX_FLAGS_RELEASE
    CMAKE_CXX_FLAGS_MINSIZEREL CMAKE_CXX_FLAGS_RELWITHDEBINFO)
    if(${flag_var} MATCHES "/MD")
        string(REGEX REPLACE "/MD" "/MT" ${flag_var} "${${flag_var}}")
    endif(${flag_var} MATCHES "/MD")
ENDFOREACH(flag_var)

0

CMakeLists.txt ที่ง่ายที่สุดที่ฉันกลั่นจากคำตอบในชุดข้อความนี้และการลองผิดลองถูกคือ:

project(test CXX C)
cmake_minimum_required(VERSION 2.6.2)

#include folder contains current project's header filed
include_directories("include")

#test folder contains test files
set (PROJECT_SOURCE_DIR test) 
add_executable(hex2base64 ${PROJECT_SOURCE_DIR}/hex2base64.cpp)

# Link test executable against gtest nothing else required
target_link_libraries(hex2base64 gtest pthread)

ควรติดตั้ง Gtest ในระบบของคุณแล้ว


การเพิ่มไลบรารีแบบนี้ใน CMake ไม่ใช่วิธีปฏิบัติที่ดี วัตถุประสงค์หลักอย่างหนึ่งของ cmake คือไม่ต้องตั้งสมมติฐานเช่น "libs นี้ควรได้รับการติดตั้งแล้ว ... " CMake ตรวจสอบว่าห้องสมุดอยู่ที่นี่และหากไม่เป็นเช่นนั้นข้อผิดพลาดจะเกิดขึ้น
Adrien BARRAL

0

เช่นเดียวกับการอัปเดตความคิดเห็นของ @ Patricia ในคำตอบที่ยอมรับและความคิดเห็นของ @ Fraser สำหรับคำถามเดิมหากคุณมีสิทธิ์เข้าถึง CMake 3.11+ คุณสามารถใช้ฟังก์ชันFetchContentของ CMake ได้

หน้า FetchContent ของ CMake ใช้ googletest เป็นตัวอย่าง!

ฉันได้แก้ไขคำตอบที่ยอมรับเล็กน้อย:

cmake_minimum_required(VERSION 3.11)
project(basic_test)

set(GTEST_VERSION 1.6.0 CACHE STRING "Google test version")

################################
# GTest
################################
FetchContent_Declare(googletest
GIT_REPOSITORY https://github.com/google/googletest.git
GIT_TAG release-${GTEST_VERSION})

FetchContent_GetProperties(googletest)
if(NOT googletest_POPULATED)
  FetchContent_Populate(googletest)
  add_subdirectory(${googletest_SOURCE_DIR} ${googletest_BINARY_DIR})
endif()

enable_testing()

################################
# Unit Tests
################################
# Add test cpp file
add_executable(runUnitTests testgtest.cpp)

# Include directories
target_include_directories(runUnitTests 
                      $<TARGET_PROPERTY:gtest,INTERFACE_SYSTEM_INCLUDE_DIRECTORIES>
                      $<TARGET_PROPERTY:gtest_main,INTERFACE_SYSTEM_INCLUDE_DIRECTORIES>)

# Link test executable against gtest & gtest_main
target_link_libraries(runUnitTests gtest
                                   gtest_main)

add_test(runUnitTests runUnitTests)

คุณสามารถใช้INTERFACE_SYSTEM_INCLUDE_DIRECTORIESคุณสมบัติเป้าหมายของเป้าหมาย gtest และ gtest_main ตามที่กำหนดไว้ในสคริปต์CMakeLists.txtการทดสอบของ Google


ใน CMake> = v3.14 คุณสามารถละทิ้ง Explicit target_include_directoriesและใช้FetchContent_MakeAvailable(googletest)แทนได้ สิ่งนี้จะเติมเนื้อหาและเพิ่มลงในบิลด์หลัก CMake FetchContent - ข้อมูลเพิ่มเติม
67hz

0

ฉันตัดสินใจที่จะโยนของทั่วไปเข้าด้วยกันอย่างรวดเร็วเพื่อแสดงให้เห็นถึงวิธีการทำที่แตกต่างจากคำตอบที่โพสต์ไว้ก่อนหน้านี้โดยหวังว่าอาจช่วยใครบางคนได้ สิ่งต่อไปนี้ใช้ได้ผลสำหรับฉันบน Mac ของฉัน ประการแรกฉันรันคำสั่งการตั้งค่าสำหรับ gtests ฉันเพิ่งใช้สคริปต์ที่พบเพื่อตั้งค่าทุกอย่าง

#!/usr/bin/env bash

# install gtests script on mac
# https://gist.github.com/butuzov/e7df782c31171f9563057871d0ae444a

#usage
# chmod +x ./gtest_installer.sh
# sudo ./gtest_installer.sh

# Current directory
__THIS_DIR=$(pwd)


# Downloads the 1.8.0 to disc
function dl {
    printf "\n  Downloading Google Test Archive\n\n"
    curl -LO https://github.com/google/googletest/archive/release-1.8.0.tar.gz
    tar xf release-1.8.0.tar.gz
}

# Unpack and Build
function build {
    printf "\n  Building GTest and Gmock\n\n"
    cd googletest-release-1.8.0
    mkdir build 
    cd $_
    cmake -Dgtest_build_samples=OFF -Dgtest_build_tests=OFF ../
    make
}

# Install header files and library
function install {
    printf "\n  Installing GTest and Gmock\n\n"

    USR_LOCAL_INC="/usr/local/include"
    GTEST_DIR="/usr/local/Cellar/gtest/"
    GMOCK_DIR="/usr/local/Cellar/gmock/"

    mkdir $GTEST_DIR

    cp googlemock/gtest/*.a $GTEST_DIR
    cp -r ../googletest/include/gtest/  $GTEST_DIR
    ln -snf $GTEST_DIR $USR_LOCAL_INC/gtest
    ln -snf $USR_LOCAL_INC/gtest/libgtest.a /usr/local/lib/libgtest.a
    ln -snf $USR_LOCAL_INC/gtest/libgtest_main.a /usr/local/lib/libgtest_main.a

    mkdir $GMOCK_DIR
    cp googlemock/*.a   $GMOCK_DIR
    cp -r ../googlemock/include/gmock/  $GMOCK_DIR
    ln -snf $GMOCK_DIR $USR_LOCAL_INC/gmock
    ln -snf $USR_LOCAL_INC/gmock/libgmock.a /usr/local/lib/libgmock.a
    ln -snf $USR_LOCAL_INC/gmock/libgmock_main.a /usr/local/lib/libgmock_main.a
}

# Final Clean up.
function cleanup {
    printf "\n  Running Cleanup\n\n"

    cd $__THIS_DIR
    rm -rf $(pwd)/googletest-release-1.8.0
    unlink $(pwd)/release-1.8.0.tar.gz
}

dl && build && install && cleanup 

ต่อไปฉันสร้างโครงสร้างโฟลเดอร์อย่างง่ายและเขียนคลาสสั้น ๆ

utils/
  cStringUtils.cpp
  cStringUtils.h
  CMakeLists.txt
utils/tests/
    gtestsMain.cpp
    cStringUtilsTest.cpp
    CMakeLists.txt

ฉันสร้าง CMakeLists.txt ระดับบนสุดสำหรับโฟลเดอร์ utils และ CMakeLists.txt สำหรับโฟลเดอร์การทดสอบ

cmake_minimum_required(VERSION 2.6)

project(${GTEST_PROJECT} C CXX)

set(CMAKE_C_STANDARD 98)
set(CMAKE_CXX_STANDARD 98)

#include .h and .cpp files in util folder
include_directories("${CMAKE_CURRENT_SOURCE_DIR}")

##########
# GTests
#########
add_subdirectory(tests)

นี่คือ CMakeLists.txt ในโฟลเดอร์การทดสอบ

cmake_minimum_required(VERSION 2.6)

set(GTEST_PROJECT gtestProject)

enable_testing()

message("Gtest Cmake")

find_package(GTest REQUIRED)

# The utils, test, and gtests directories
include_directories("${CMAKE_CURRENT_SOURCE_DIR}")
include_directories("/usr/local/Cellar/gtest/include")
include_directories("/usr/local/Cellar/gtest/lib")

set(SOURCES
  gtestsMain.cpp
  ../cStringUtils.cpp
  cStringUtilsTest.cpp
)

set(HEADERS
  ../cStringUtils.h
)

add_executable(${GTEST_PROJECT} ${SOURCES})
target_link_libraries(${GTEST_PROJECT} PUBLIC
  gtest
  gtest_main
)

add_test(${GTEST_PROJECT} ${GTEST_PROJECT})

จากนั้นสิ่งที่เหลือก็คือการเขียนตัวอย่าง gtest และ gtest main

gtest ตัวอย่าง

#include "gtest/gtest.h"
#include "cStringUtils.h"

namespace utils
{

class cStringUtilsTest : public ::testing::Test {

 public:

  cStringUtilsTest() : m_function_param(10) {}
  ~cStringUtilsTest(){}

 protected:
  virtual void SetUp() 
  {
    // declare pointer 
    pFooObject = new StringUtilsC();    
  }

  virtual void TearDown() 
  {
    // Code here will be called immediately after each test
    // (right before the destructor).
    if (pFooObject != NULL)
    {
      delete pFooObject;
      pFooObject = NULL;
    }
  }


  StringUtilsC fooObject;              // declare object
  StringUtilsC *pFooObject;
  int m_function_param;                // this value is used to test constructor
};

TEST_F(cStringUtilsTest, testConstructors){
    EXPECT_TRUE(1);

  StringUtilsC fooObject2 = fooObject; // use copy constructor


  fooObject.fooFunction(m_function_param);
  pFooObject->fooFunction(m_function_param);
  fooObject2.fooFunction(m_function_param);
}

} // utils end

ตัวอย่าง gtest main

#include "gtest/gtest.h"
#include "cStringUtils.h"

int main(int argc, char **argv) {
  ::testing::InitGoogleTest(&argc, argv); 
  return RUN_ALL_TESTS();
}

จากนั้นฉันสามารถคอมไพล์และรัน gtests ด้วยคำสั่งต่อไปนี้จากโฟลเดอร์ utils

cmake .
make 
./tests/gtestProject
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.