Lorenz
Lorenz

Reputation: 513

How to shadow a header file with CMake for unit-testing

This is the simplified folder structure I have:

+ production
+-- ClassToTest.cpp (contains '#includes "DragonHeader.h"')
+-- ClassToTest.h
+-- DragonHeader.h (has a lot of dependencies, ClassToTest only need one simple static function with no dependencies at all.)
+ tests
+-- tst_ClassToTest.cpp
+-- DragonHeader.h (which defines and implements the needed simple function)

So for the test case I'd like that tests/DragonHeader.h shadows production/DragonHeader.h. => ClassToTest.cpp includes tests/DragonHeader.h. How can that be achieved? (I am working with MSVC 2015 if it is relevant...)

The CMakeLists.txt in the tests folder looks like

project( tst_ClassToTest )
set( ${PROJECT_NAME}_SOURCES tst_ClassToTest.cpp DragonHeader.h ../production/ClassToTest.cpp )
# How to force ClassToTest.cpp to use DragonHeader.h, not production/DragonHeader.h?
add_executable( ${PROJECT_NAME} WIN32 ${${PROJECT_NAME}_SOURCES} )

Thanks!

Disclaimer: I seek for a solution that does not require me to touch ClassToTest.cpp or to touch the code in production including the related CMakeLists.txt files at all. One solution, however, is to use CMake to copy ClassToTest.cpp/h into the tests folder, but I consider it sub-optimal.

Upvotes: 1

Views: 1182

Answers (1)

Th. Thielemann
Th. Thielemann

Reputation: 2825

My first thought was to use different include_directory statements for both production and unit test. But in this case the other header file ClassToTest.h must be in a different folder. Or you have to moveDragonHeader.h into another folder.

# CMake for production
include_directory(production)
include_directory(production_dragon)

#CMake for test
include_directory(production)
include_directory(test_dragon)

Another way could be an

#ifndef USE_TEST_HEADERS
#include "DragonHeaderTest.h"
#else
#include "DragonHeader.h"
#endif

in ClassToTest.cpp. To set the define add into your test/CMakeLists.txt file the string -DUSE_TEST_HEADERS to the compiler flags.

Third solution is to replace production/DragonHeader.h by a copy of test/DragonHeader.h in advanced of make. This works only in case production/DragonHeader.h can be restored. Either from a file system copy or from your Configuration Mgmt. System. This can by achieved by wrap the bild into a script. Don't know whether MSVC 2015 can trigger such a script instead of build.

rem Build for tests
rem Run cmake 
cmake PARAMETERS
rem Prepare unit test
cp WHATEVER
rem nmake
name PARAMETERS

Upvotes: 1

Related Questions