Skip to content

Commit 7d3040d

Browse files
authored
Merge pull request #109 from fdefelici/107-cmake-make-header-library-interoperable-with-find_package
107 cmake make header library interoperable with find package
2 parents 1b69357 + 3c04be9 commit 7d3040d

File tree

4 files changed

+127
-18
lines changed

4 files changed

+127
-18
lines changed

CMakeLists.txt

Lines changed: 73 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,85 @@
11
cmake_minimum_required(VERSION 3.18)
2-
project(CLoveUnit LANGUAGES C)
32

3+
set(CLOVE_SOURCE_DIR ${CMAKE_CURRENT_LIST_DIR})
4+
list(INSERT CMAKE_MODULE_PATH 0 ${CLOVE_SOURCE_DIR}/cmake/modules)
5+
6+
# Extract CLOVE_VERSION from header file
7+
set(CLOVE_VERSION_REGEX "#define __CLOVE_VERSION_.*[ \t]+(.+)")
8+
file(STRINGS "${CLOVE_SOURCE_DIR}/clove-unit.h" CLOVE_VERSION REGEX ${CLOVE_VERSION_REGEX})
9+
list(TRANSFORM CLOVE_VERSION REPLACE ${CLOVE_VERSION_REGEX} "\\1")
10+
string(JOIN "." CLOVE_VERSION ${CLOVE_VERSION})
11+
12+
# Configure Project
13+
project(
14+
CLoveUnit
15+
VERSION ${CLOVE_VERSION}
16+
DESCRIPTION "Single-header Unit Testing framework for C (interoperable with C++) with test autodiscovery feature"
17+
HOMEPAGE_URL "https://github.com/fdefelici/clove-unit"
18+
LANGUAGES C
19+
)
20+
21+
include(JoinPaths)
22+
include(GNUInstallDirs)
23+
include(CMakePackageConfigHelpers)
24+
25+
join_paths(CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}" clove-unit ${PROJECT_VERSION})
26+
27+
# Library Target definition and configuration
428
add_library(clove-unit INTERFACE)
5-
target_include_directories(clove-unit INTERFACE "${CMAKE_CURRENT_LIST_DIR}")
29+
add_library(clove-unit::clove-unit ALIAS clove-unit)
30+
31+
target_include_directories(
32+
clove-unit INTERFACE
33+
$<BUILD_INTERFACE:${CLOVE_SOURCE_DIR}>
34+
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
35+
)
36+
637
target_compile_features(clove-unit INTERFACE c_std_11)
738

8-
#[[
9-
add_subdirectory(tests/functs)
10-
if (DEFINED CLOVE_CMAKE__CI_TRIGGERED)
11-
add_subdirectory(tests/stricts/clove-c)
12-
add_subdirectory(tests/stricts/clove-cpp)
13-
add_subdirectory(examples/clove101)
14-
add_subdirectory(examples/clovepp)
15-
endif()
39+
# Install command stuffs for enabling find_package usage
40+
install(
41+
TARGETS clove-unit
42+
EXPORT clove-unit-targets
43+
INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
44+
)
45+
46+
write_basic_package_version_file(
47+
clove-unit-config-version.cmake
48+
VERSION ${PROJECT_VERSION}
49+
COMPATIBILITY AnyNewerVersion
50+
)
51+
52+
configure_package_config_file(
53+
${CLOVE_SOURCE_DIR}/cmake/in/clove-unit-config.cmake.in
54+
clove-unit-config.cmake
55+
INSTALL_DESTINATION ${CMAKE_INSTALL_PREFIX}/cmake
56+
)
57+
58+
install(
59+
FILES ${CLOVE_SOURCE_DIR}/clove-unit.h
60+
DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
61+
)
62+
63+
install(
64+
FILES
65+
${PROJECT_BINARY_DIR}/clove-unit-config.cmake
66+
${PROJECT_BINARY_DIR}/clove-unit-config-version.cmake
67+
DESTINATION ${CMAKE_INSTALL_PREFIX}/cmake
68+
)
69+
70+
install(
71+
EXPORT clove-unit-targets
72+
#NAMESPACE clove-unit::
73+
DESTINATION ${CMAKE_INSTALL_PREFIX}/cmake
74+
)
75+
76+
export(PACKAGE clove-unit)
1677

17-
if (DEFINED CLOVE_CMAKE__ENABLE_PERFS)
18-
add_subdirectory(tests/perfs)
19-
endif()
20-
]]
2178

2279
#[[
2380
In case this is the root project add dev targets (Development mode).
2481
To avoid targets pollution when using FetchContent were only the target library is required
82+
Note: PROJECT_IS_TOP_LEVEL cmake variable exists in version 3.21+
2583
]]
2684
if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR)
2785
include(CTest)
@@ -42,4 +100,4 @@ if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR)
42100
add_subdirectory(tests/perfs)
43101
endif()
44102

45-
endif()
103+
endif()

README.md

Lines changed: 26 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -70,9 +70,9 @@ Then remember to properly configure your compiler include paths.
7070
* [Conan](https://conan.io): read [here](https://conan.io/center/recipes/clove-unit) for details on how to import it.
7171

7272
### Using CMake
73-
In case you still need dependency management, but you want to avoid Package Manager configuration complexity, you can use standard mechansim provided by `CMake` such as [FetchContent](https://cmake.org/cmake/help/latest/module/FetchContent.html) and [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html).
73+
In case you still need dependency management, but you want to avoid Package Manager configuration complexity, you can use standard mechansim provided by `CMake` such as [FetchContent](https://cmake.org/cmake/help/latest/module/FetchContent.html), [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html) and [find_package](https://cmake.org/cmake/help/latest/command/find_package.html).
7474

75-
> CMake library is named `clove-unit`
75+
> NOTE: CMake library is named `clove-unit`
7676
7777
Here a few examples:
7878

@@ -94,7 +94,7 @@ Here a few examples:
9494
target_link_libraries(tests clove-unit)
9595
```
9696

97-
* [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html)
97+
* **add_subdirectory**
9898

9999
First download `CLove-Unit` repository and then point properly to it like this:
100100

@@ -108,6 +108,29 @@ Here a few examples:
108108
target_link_libraries(tests clove-unit)
109109
```
110110

111+
* **find_package**
112+
113+
First download `CLove-Unit` repository and then run cmake install command on it.
114+
115+
Package will be installed in at following path: `<CMAKE_INSTALL_PREFIX/clove-unit/<CLOVE_VERSION>`
116+
117+
Eventually you may want to customize [CMAKE_INSTALL_PREFIX](https://cmake.org/cmake/help/latest/variable/CMAKE_INSTALL_PREFIX.html) variable to override cmake default installation path for packages.
118+
119+
120+
Then use the package as follow:
121+
```cmake
122+
cmake_minimum_required(VERSION 3.18)
123+
project(TestProject C)
124+
125+
find_package(clove-unit REQUIRED PATHS <INSTALLATION_PATH>)
126+
127+
# or more strict
128+
# find_package(clove-unit <CLOVE_VERSION> EXACT REQUIRED PATHS <INSTALLATION_PATH>)
129+
130+
add_executable(tests <YOUR_TEST_FILES>)
131+
target_link_libraries(tests clove-unit)
132+
```
133+
111134
## How It Works
112135

113136
`CLove-Unit` is built upon these fundamental concepts:

cmake/in/clove-unit-config.cmake.in

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
@PACKAGE_INIT@
2+
3+
set(CLOVE_VERSION "@PROJECT_VERSION@")
4+
include("${CMAKE_CURRENT_LIST_DIR}/clove-unit-targets.cmake")
5+
check_required_components("@PROJECT_NAME@")

cmake/modules/JoinPaths.cmake

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
# This module provides function for joining paths
2+
# known from most languages
3+
#
4+
# SPDX-License-Identifier: (MIT OR CC0-1.0)
5+
# Copyright 2020 Jan Tojnar
6+
# https://github.com/jtojnar/cmake-snips
7+
#
8+
# Modelled after Python’s os.path.join
9+
# https://docs.python.org/3.7/library/os.path.html#os.path.join
10+
# Windows not supported
11+
function(join_paths joined_path first_path_segment)
12+
set(temp_path "${first_path_segment}")
13+
foreach(current_segment IN LISTS ARGN)
14+
if(NOT ("${current_segment}" STREQUAL ""))
15+
if(IS_ABSOLUTE "${current_segment}")
16+
set(temp_path "${current_segment}")
17+
else()
18+
set(temp_path "${temp_path}/${current_segment}")
19+
endif()
20+
endif()
21+
endforeach()
22+
set(${joined_path} "${temp_path}" PARENT_SCOPE)
23+
endfunction()

0 commit comments

Comments
 (0)