2
0
mirror of https://github.com/boostorg/url.git synced 2026-01-19 04:42:15 +00:00
Files
url/extra/test_suite/DiscoverTests.cmake
2025-07-11 01:51:59 +00:00

108 lines
4.8 KiB
CMake

#
# Copyright (c) 2025 Alan de Freitas (alandefreitas@gmail.com)
#
# Distributed under the Boost Software License, Version 1.0. (See accompanying
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#
# Official repository: https://github.com/boostorg/url
#
# Function to register tests with CTest
#
# This function discovers tests from an executable target that uses the Boost.URL test suite
# and creates individual CTest targets for each test.
#
# Arguments:
# - TARGET: The name of the target that contains the tests (e.g., boost_url_unit_tests).
#
# Options:
# - TEST_SPEC arg1: List of test specifications to run.
# - EXTRA_ARGS arg1: Additional arguments to pass to the test executable.
# - WORKING_DIRECTORY dir: Working directory for the tests.
# - TEST_PREFIX prefix: Prefix for the test names. Useful when there are multiple calls to this function.
# - TEST_SUFFIX suffix: Suffix for the test names. Useful when there are multiple calls to this function.
# - PROPERTIES name1 value1: Additional properties to set for all tests.
#
# The idea was inspired by the Catch2 library.
#
function(boost_url_test_suite_discover_tests TARGET)
cmake_parse_arguments(
# prefix
"TEST_SUITE"
# options
""
# single-value arguments
"TEST_PREFIX;TEST_SUFFIX;WORKING_DIRECTORY"
# multi-value arguments
"TEST_SPEC;EXTRA_ARGS;PROPERTIES"
# arguments
${ARGN}
)
# Adjust command line arguments
if (NOT TEST_SUITE_WORKING_DIRECTORY)
set(TEST_SUITE_WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
endif ()
# Generate a unique name based on the test specs
string(SHA1 TEST_SUITE_ARGS_HASH "${TEST_SUITE_TEST_SPEC}")
string(SUBSTRING ${TEST_SUITE_ARGS_HASH} 0 7 TEST_SUITE_ARGS_HASH)
# After building the TARGET, use CMake and the executable to create the
# tests cmake script ${TEST_SUITE_CTEST_TESTS_FILE}.
# Our CMake script will include this test script to create the test
# targets for each test.
set(TEST_SUITE_CTEST_TESTS_FILE "${CMAKE_CURRENT_BINARY_DIR}/${TARGET}-${TEST_SUITE_ARGS_HASH}_tests.cmake")
add_custom_command(
TARGET ${TARGET}
POST_BUILD
BYPRODUCTS "${TEST_SUITE_CTEST_TESTS_FILE}"
COMMAND "${CMAKE_COMMAND}"
-D "TEST_SUITE_SCRIPT_DEBUG=${TEST_SUITE_SCRIPT_DEBUG}"
-D "TEST_TARGET=${TARGET}"
-D "TEST_EXECUTABLE=$<TARGET_FILE:${TARGET}>"
-D "TEST_WORKING_DIR=${TEST_SUITE_WORKING_DIRECTORY}"
-D "TEST_SPEC=${TEST_SUITE_TEST_SPEC}"
-D "TEST_EXTRA_ARGS=${TEST_SUITE_EXTRA_ARGS}"
-D "TEST_PROPERTIES=${TEST_SUITE_PROPERTIES}"
-D "TEST_PREFIX=${TEST_SUITE_TEST_PREFIX}"
-D "TEST_SUFFIX=${TEST_SUITE_TEST_SUFFIX}"
-D "CTEST_FILE=${TEST_SUITE_CTEST_TESTS_FILE}"
-P "${TEST_SUITE_DISCOVER_AND_WRITE_TESTS_SCRIPT}"
VERBATIM
)
# Include the generated test file to define the tests
# The TEST_SUITE_CTEST_INCLUDE_FILE file we will include to define the tests
# The {...}_include.cmake file is a simple script that includes the {}_tests.cmake file
# when it exists. If it does not exist, it will create a dummy test.
# This is useful to avoid errors when the target that creates the tests is not built
# for some reason.
set(TEST_SUITE_CTEST_INCLUDE_FILE "${CMAKE_CURRENT_BINARY_DIR}/${TARGET}-${TEST_SUITE_ARGS_HASH}_include.cmake")
file(WRITE "${TEST_SUITE_CTEST_INCLUDE_FILE}"
"# This file is automatically generated by CMake to include the tests for the target ${TARGET}.\n"
"# It includes the tests from the file ${TEST_SUITE_CTEST_TESTS_FILE}.\n"
"if (EXISTS \"${TEST_SUITE_CTEST_TESTS_FILE}\")\n"
" include(\"${TEST_SUITE_CTEST_TESTS_FILE}\")\n"
"else()\n"
" # If the tests file does not exist, create a dummy test to avoid errors.\n"
" # The tests file will not exist if we have not run the cmake build step yet.\n"
" add_test(${TARGET}_NOT_BUILT-${TEST_SUITE_ARGS_HASH} ${TARGET}_NOT_BUILT-${TEST_SUITE_ARGS_HASH})\n"
"endif ()\n"
)
# Add discovered tests to directory TEST_INCLUDE_FILES
# This directory property specifies a list of CMake scripts to be included and
# processed when ctest runs on the directory. The scripts are processed when running
# ctest, not during the cmake configuration phase.
# https://cmake.org/cmake/help/latest/prop_dir/TEST_INCLUDE_FILES.html
set_property(DIRECTORY
APPEND PROPERTY TEST_INCLUDE_FILES "${TEST_SUITE_CTEST_INCLUDE_FILE}"
)
endfunction()
set(TEST_SUITE_DISCOVER_AND_WRITE_TESTS_SCRIPT
${CMAKE_CURRENT_LIST_DIR}/DiscoverAndWriteTestsScripts.cmake
CACHE INTERNAL "Path to the script that discovers tests for the test suite"
)