Support multiple source directories in `srcdirref` file

* Locate test files in all source directories specified in `srcdirref`
* Allow overriding contents of `srcdirref` so the directory of another
  component (within the same repository) can be appended to share testfiles
This commit is contained in:
Martchus 2023-02-27 18:01:14 +01:00
parent a703813b4c
commit 2b6f26895d
3 changed files with 24 additions and 15 deletions

View File

@ -344,7 +344,10 @@ endif ()
# useful if there's a test target; this is for instance also used in mocked configuration of syncthingtray) -> add a file # useful if there's a test target; this is for instance also used in mocked configuration of syncthingtray) -> add a file
# called "srcdirref" to the build directory; this file contains the path of the sources so tests can easily find test files # called "srcdirref" to the build directory; this file contains the path of the sources so tests can easily find test files
# contained in the source directory # contained in the source directory
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/srcdirref" "${CMAKE_CURRENT_SOURCE_DIR}") if (NOT META_SRCDIR_REFS)
set(META_SRCDIR_REFS "${CMAKE_CURRENT_SOURCE_DIR}")
endif ()
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/srcdirref" "${META_SRCDIR_REFS}")
# -> ensure the directory "testfiles" exists in the build directory; tests of my projects use it by default to create working # -> ensure the directory "testfiles" exists in the build directory; tests of my projects use it by default to create working
# copies of testfiles # copies of testfiles
file(MAKE_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/testfiles") file(MAKE_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/testfiles")

View File

@ -178,7 +178,7 @@ TestApplication::TestApplication(int argc, const char *const *argv)
} }
// -> find source directory // -> find source directory
if (auto testFilePathFromSrcDirRef = readTestfilePathFromSrcRef(); !testFilePathFromSrcDirRef.empty()) { if (auto testFilePathFromSrcDirRef = readTestfilePathFromSrcRef(); !testFilePathFromSrcDirRef.empty()) {
m_testFilesPaths.emplace_back(std::move(testFilePathFromSrcDirRef)); m_testFilesPaths.insert(m_testFilesPaths.end(), std::make_move_iterator(testFilePathFromSrcDirRef.begin()), std::make_move_iterator(testFilePathFromSrcDirRef.end()));
} }
// -> try testfiles directory in working directory // -> try testfiles directory in working directory
m_testFilesPaths.emplace_back("./testfiles/"); m_testFilesPaths.emplace_back("./testfiles/");
@ -612,10 +612,11 @@ string TestApplication::readTestfilePathFromEnv()
* \remarks That file is supposed to contain the path the the source directory. It is supposed to be stored by the build system in the * \remarks That file is supposed to contain the path the the source directory. It is supposed to be stored by the build system in the
* same directory as the test executable. The CMake modules contained of these utilities ensure that's the case. * same directory as the test executable. The CMake modules contained of these utilities ensure that's the case.
*/ */
string TestApplication::readTestfilePathFromSrcRef() std::vector<std::string> TestApplication::readTestfilePathFromSrcRef()
{ {
// find the path of the current executable on platforms supporting "/proc/self/exe"; otherwise assume the current working directory // find the path of the current executable on platforms supporting "/proc/self/exe"; otherwise assume the current working directory
// is the executable path // is the executable path
auto res = std::vector<std::string>();
auto binaryPath = std::string(); auto binaryPath = std::string();
#if defined(CPP_UTILITIES_USE_STANDARD_FILESYSTEM) && defined(PLATFORM_UNIX) #if defined(CPP_UTILITIES_USE_STANDARD_FILESYSTEM) && defined(PLATFORM_UNIX)
try { try {
@ -628,25 +629,30 @@ string TestApplication::readTestfilePathFromSrcRef()
const auto srcdirrefPath = binaryPath + "srcdirref"; const auto srcdirrefPath = binaryPath + "srcdirref";
try { try {
// read "srcdirref" file which should contain the path of the source directory // read "srcdirref" file which should contain the path of the source directory
auto srcDirContent(readFile(srcdirrefPath, 2 * 1024)); const auto srcDirContent = readFile(srcdirrefPath, 2 * 1024);
if (srcDirContent.empty()) { if (srcDirContent.empty()) {
cerr << Phrases::Warning << "The file \"srcdirref\" is empty." << Phrases::EndFlush; cerr << Phrases::Warning << "The file \"srcdirref\" is empty." << Phrases::EndFlush;
return string(); return res;
} }
srcDirContent += "/testfiles/";
// check whether the referenced source directory contains a "testfiles" directory // check whether the referenced source directories contain a "testfiles" directory
if (!dirExists(srcDirContent)) { const auto srcPaths = splitStringSimple<std::vector<std::string_view>>(srcDirContent, "\n");
cerr << Phrases::Warning for (const auto &srcPath : srcPaths) {
<< "The source directory referenced by the file \"srcdirref\" does not contain a \"testfiles\" directory or does not exist." auto testfilesPath = argsToString(srcPath, "/testfiles/");
<< Phrases::End << "Referenced source directory: " << srcDirContent << endl; if (dirExists(testfilesPath)) {
return string(); res.emplace_back(std::move(testfilesPath));
} else {
cerr << Phrases::Warning
<< "The source directory referenced by the file \"srcdirref\" does not contain a \"testfiles\" directory or does not exist."
<< Phrases::End << "Referenced source directory: " << testfilesPath << endl;
}
} }
return srcDirContent; return res;
} catch (const std::ios_base::failure &e) { } catch (const std::ios_base::failure &e) {
cerr << Phrases::Warning << "The file \"" << srcdirrefPath << "\" can not be opened: " << e.what() << Phrases::EndFlush; cerr << Phrases::Warning << "The file \"" << srcdirrefPath << "\" can not be opened: " << e.what() << Phrases::EndFlush;
} }
return string(); return res;
} }
} // namespace CppUtilities } // namespace CppUtilities

View File

@ -52,7 +52,7 @@ public:
private: private:
static std::string readTestfilePathFromEnv(); static std::string readTestfilePathFromEnv();
static std::string readTestfilePathFromSrcRef(); static std::vector<std::string> readTestfilePathFromSrcRef();
ArgumentParser m_parser; ArgumentParser m_parser;
OperationArgument m_listArg; OperationArgument m_listArg;