J'essaye de structurer mon projet pour inclure les sources de production (dans le src
sous-dossier) et les tests (dans le test
sous-dossier). J'utilise CMake pour construire ceci. À titre d'exemple minimal, j'ai les fichiers suivants:
CMakeLists.txt:
cmake_minimum_required (VERSION 2.8)
project (TEST)
add_subdirectory (src)
add_subdirectory (test)
src / CMakeLists.txt:
add_executable (demo main.cpp sqr.cpp)
src / sqr.h
#ifndef SQR_H
#define SQR_H
double sqr(double);
#endif // SQR_H
src / sqr.cpp
#include "sqr.h"
double sqr(double x) { return x*x; }
src / main.cpp - utilise sqr, cela n'a pas vraiment d'importance
test / CMakeLists.txt:
find_package(Boost COMPONENTS system filesystem unit_test_framework REQUIRED)
include_directories (${TEST_SOURCE_DIR}/src)
ADD_DEFINITIONS(-DBOOST_TEST_DYN_LINK)
add_executable (test test.cpp ${TEST_SOURCE_DIR}/src/sqr.cpp)
target_link_libraries(test
${Boost_FILESYSTEM_LIBRARY}
${Boost_SYSTEM_LIBRARY}
${Boost_UNIT_TEST_FRAMEWORK_LIBRARY}
)
enable_testing()
add_test(MyTest test)
test / test.cpp:
#define BOOST_TEST_MODULE SqrTests
#include <boost/test/unit_test.hpp>
#include "sqr.h"
BOOST_AUTO_TEST_CASE(FailTest)
{
BOOST_CHECK_EQUAL(5, sqr(2));
}
BOOST_AUTO_TEST_CASE(PassTest)
{
BOOST_CHECK_EQUAL(4, sqr(2));
}
Quelques questions:
- Cette structure a-t-elle un sens? Quelles sont les meilleures pratiques lors de la structuration de ce code? (Je viens de C # et java, et là c'est plus facile dans un sens)
- Je n'aime pas le fait que je doive lister tous les fichiers du
src
dossier dans letest/CMakeLists.txt
fichier. S'il s'agissait d'un projet de bibliothèque, je lierais simplement la bibliothèque. Existe-t-il un moyen d'éviter de lister tous les fichiers cpp de l'autre projet? - Quelles sont les lignes
enable_testing()
etadd_test(MyTest test)
faire? Je n'ai vu aucun effet. Comment puis-je exécuter les tests depuis CMake (ou CTest)? - Jusqu'à présent, je viens de courir
cmake .
dans le dossier racine, mais cela a créé un désordre avec des fichiers temporaires partout. Comment puis-je obtenir les résultats de la compilation dans une structure raisonnable?
c++
unit-testing
boost
cmake
boost-test
Grzenio
la source
la source
Réponses:
Pour les questions 1 et 2, je recommanderais de créer une bibliothèque à partir de vos fichiers non test à l'exclusion de main.cpp (dans ce cas, juste src / sqr.cpp et src / sqr.h), puis vous pouvez éviter de lister (et plus important encore) recompilation) toutes les sources deux fois.
Pour la question 3, ces commandes ajoutent un test appelé "MyTest" qui invoque votre exécutable "test" sans aucun argument. Cependant, puisque vous avez ajouté ces commandes à test / CMakeLists.txt et non à votre CMakeLists.txt de niveau supérieur, vous ne pouvez appeler le test qu'à partir du sous-répertoire "test" de votre arborescence de construction (essayez
cd test && ctest -N
). Si vous voulez que le test soit exécutable à partir de votre répertoire de construction de niveau supérieur, vous devez appeler àadd_test
partir du CMakeLists.txt de niveau supérieur. Cela signifie également que vous devez utiliser la forme la plus détaillée deadd_test
puisque votre exe de test n'est pas défini dans le même CMakeLists.txtDans votre cas, puisque vous exécutez cmake dans le dossier racine, votre arborescence de construction et votre arborescence source sont identiques. Ceci est connu sous le nom de build in-source et n'est pas idéal, ce qui conduit à la question 4.
La méthode préférée pour générer l'arborescence de construction est de faire une construction hors source, c'est-à-dire de créer un répertoire quelque part en dehors de votre arbre source et d'exécuter cmake à partir de là. Même la création d'un répertoire "build" à la racine de votre projet et son exécution
cmake ..
fourniraient une structure propre qui n'interférera pas avec votre arborescence source.Un dernier point est d'éviter d'appeler les exécutables "test" (sensible à la casse). Pour connaître les raisons, lisez cette réponse .
Pour réaliser ces changements, je ferais ce qui suit:
CMakeLists.txt:
src / CMakeLists.txt:
test / CMakeLists.txt:
la source
project (TEST)
- voir cmake.org/cmake/help/v3.6/variable/PROJECT-NAME_SOURCE_DIR.htmlJ'aime l'exemple de @Fraser mais j'utiliserais la commande add_test dans le test / CMakeLists.txt et utiliserais enable_testing avant add_subdirectory (test).
De cette façon, vous pouvez exécuter vos tests à partir du répertoire de construction de niveau supérieur tout en spécifiant vos tests dans le fichier test / CMakeLists.txt.
Le résultat ressemblerait à ceci (j'ai réutilisé l'exemple de @Fraser):
CMakeLists.txt
src / CMakeLists.txt
test / CMakeLists.txt
la source
ctest -N
jusqu'à ce que vous ayez reçu une astuce sur l'activation des tests avant d'ajouter le sous-répertoire.