From 83e20162d70894cdfafb1b2dde73df877994e504 Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 08:03:33 +0100 Subject: [PATCH 01/11] Add code coverage CMake configuration --- CMakeLists.txt | 6 ++++-- cmake/CodeCoverage.cmake | 15 +++++++++++++++ src/CMakeLists.txt | 1 + 3 files changed, 20 insertions(+), 2 deletions(-) create mode 100644 cmake/CodeCoverage.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 772e787..f1da020 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -4,9 +4,11 @@ project(cppIni LANGUAGES CXX VERSION 0.1.0) set(CMAKE_CXX_STANDARD 20) set(CMAKE_CXX_STANDARD_REQUIRED ON) -option(BUILD_TESTING ON "Build test files") -option(BUILD_SHARED_LIBS ON "Build shared library files") +option(BUILD_TESTING "Build test files" ON) +option(BUILD_SHARED_LIBS "Build shared library files" ON) +option(CODE_COVERAGE "Enable coverage reporting" OFF) +include(cmake/CodeCoverage.cmake) add_subdirectory(src) if(BUILD_TESTING) diff --git a/cmake/CodeCoverage.cmake b/cmake/CodeCoverage.cmake new file mode 100644 index 0000000..611780a --- /dev/null +++ b/cmake/CodeCoverage.cmake @@ -0,0 +1,15 @@ +cmake_minimum_required(VERSION 3.24) + +# Code coverage configuration +add_library(coverage_config INTERFACE) +if(CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID MATCHES "GNU|Clang") + message("Enabling code coverage") + target_compile_options(coverage_config INTERFACE + -O0 # no optimization + -g # generate debug info + --coverage # sets all required flags + -fprofile-arcs # generate profile information for arcs + -ftest-coverage # generate profile information for test coverage + ) + target_link_options(coverage_config INTERFACE --coverage) +endif() diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 268dd6c..1cd90d7 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -21,6 +21,7 @@ set(PRIVATE_HEADERS ) add_library(${PROJECT_NAME} ${SOURCES} ${API_HEADERS} ${PRIVATE_HEADERS}) +target_link_libraries(${PROJECT_NAME} PUBLIC coverage_config) include(GenerateExportHeader) string(TOLOWER ${PROJECT_NAME} PROJECT_NAME_LOWER) From e66231e31eec7acdb3ea80c9cdda5e5246cd2005 Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 08:05:12 +0100 Subject: [PATCH 02/11] Build in code coverage mode --- .github/workflows/build.yaml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index e35ee3f..6cbb061 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -90,7 +90,8 @@ jobs: -DCMAKE_BUILD_TYPE=${{ matrix.build_type }} -DCMAKE_CXX_COMPILER=${{ matrix.cpp_compiler }} -DCMAKE_C_COMPILER=${{ matrix.c_compiler }} - -DBUILD_TESTING=ON + -DBUILD_TESTING=ON + -DCODE_COVERAGE=ON --toolchain=conan_toolchain.cmake -S ${{ github.workspace }} From 2ae543fe4075b61c8f85556b06db9670536a5018 Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 08:06:37 +0100 Subject: [PATCH 03/11] Add coverage report upload to codecov.io --- .github/workflows/build.yaml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index 6cbb061..b534336 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -101,3 +101,10 @@ jobs: - name: 🏃 Run test suite working-directory: build run: ctest --build-config ${{ matrix.build_type }} + + - name: ☂️ Upload coverage reports to Codecov + uses: codecov/codecov-action@v3 + if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' + env: + CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} + From 8256b0246614a273eed6ee9974936898097e12b7 Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 14:05:50 +0100 Subject: [PATCH 04/11] Remove unnecessary compile options --- cmake/CodeCoverage.cmake | 2 -- 1 file changed, 2 deletions(-) diff --git a/cmake/CodeCoverage.cmake b/cmake/CodeCoverage.cmake index 611780a..5363f57 100644 --- a/cmake/CodeCoverage.cmake +++ b/cmake/CodeCoverage.cmake @@ -8,8 +8,6 @@ if(CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID MATCHES "GNU|Clang") -O0 # no optimization -g # generate debug info --coverage # sets all required flags - -fprofile-arcs # generate profile information for arcs - -ftest-coverage # generate profile information for test coverage ) target_link_options(coverage_config INTERFACE --coverage) endif() From cc0aa0669e0dfe4b06557ef00325f8f7c860067c Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 14:06:03 +0100 Subject: [PATCH 05/11] Only build coverage on gcc --- cmake/CodeCoverage.cmake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmake/CodeCoverage.cmake b/cmake/CodeCoverage.cmake index 5363f57..6b3a811 100644 --- a/cmake/CodeCoverage.cmake +++ b/cmake/CodeCoverage.cmake @@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.24) # Code coverage configuration add_library(coverage_config INTERFACE) -if(CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID MATCHES "GNU|Clang") +if(CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID MATCHES "GNU") message("Enabling code coverage") target_compile_options(coverage_config INTERFACE -O0 # no optimization From 9c3b774c167631c6ed4e99bb73ae2c7e112655ca Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 14:06:33 +0100 Subject: [PATCH 06/11] Generate coverage report with gcovr --- .github/workflows/build.yaml | 4 ++++ requirements.txt | 1 + 2 files changed, 5 insertions(+) diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index b534336..6db0630 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -102,6 +102,10 @@ jobs: working-directory: build run: ctest --build-config ${{ matrix.build_type }} + - name: 📊 Generate coverage reports + if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' + run: gcovr --cobertura --exclude-unreachable-branches --exclude-throw-branches --root ${{ github.workspace }} --output coverage.xml + - name: ☂️ Upload coverage reports to Codecov uses: codecov/codecov-action@v3 if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' diff --git a/requirements.txt b/requirements.txt index 45f9eee..c5cc328 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1 +1,2 @@ conan >= 2.0.10 +gcovr >= 6.0 From 4ec19d09ab55eed1e58fd5f51025de44cae12933 Mon Sep 17 00:00:00 2001 From: Master92 Date: Fri, 1 Dec 2023 14:10:00 +0100 Subject: [PATCH 07/11] Fix cobertura output path --- .github/workflows/build.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index 6db0630..4926c41 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -104,7 +104,7 @@ jobs: - name: 📊 Generate coverage reports if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' - run: gcovr --cobertura --exclude-unreachable-branches --exclude-throw-branches --root ${{ github.workspace }} --output coverage.xml + run: gcovr --exclude-unreachable-branches --exclude-throw-branches --root ${{ github.workspace }} --cobertura coverage.xml - name: ☂️ Upload coverage reports to Codecov uses: codecov/codecov-action@v3 From 35aa0beb6a3bef09269366a7dfdd9ee4ee95fa13 Mon Sep 17 00:00:00 2001 From: Master92 Date: Mon, 4 Dec 2023 07:46:17 +0100 Subject: [PATCH 08/11] Remove direct gcovr requirement and use action --- .github/workflows/build.yaml | 2 +- requirements.txt | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index 4926c41..948a807 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -104,7 +104,7 @@ jobs: - name: 📊 Generate coverage reports if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' - run: gcovr --exclude-unreachable-branches --exclude-throw-branches --root ${{ github.workspace }} --cobertura coverage.xml + uses: threeal/gcovr-action@v1.0.0 - name: ☂️ Upload coverage reports to Codecov uses: codecov/codecov-action@v3 diff --git a/requirements.txt b/requirements.txt index c5cc328..45f9eee 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,2 +1 @@ conan >= 2.0.10 -gcovr >= 6.0 From c14f06560eddd81caeccb580b43cd3de20a88b95 Mon Sep 17 00:00:00 2001 From: Master92 Date: Mon, 4 Dec 2023 10:36:52 +0100 Subject: [PATCH 09/11] Move coverage generation to extra workflow --- .github/workflows/build.yaml | 13 +------ .github/workflows/coverage.yaml | 66 +++++++++++++++++++++++++++++++++ 2 files changed, 67 insertions(+), 12 deletions(-) create mode 100644 .github/workflows/coverage.yaml diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index 948a807..cbf134f 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -91,7 +91,7 @@ jobs: -DCMAKE_CXX_COMPILER=${{ matrix.cpp_compiler }} -DCMAKE_C_COMPILER=${{ matrix.c_compiler }} -DBUILD_TESTING=ON - -DCODE_COVERAGE=ON + -DCODE_COVERAGE=OFF --toolchain=conan_toolchain.cmake -S ${{ github.workspace }} @@ -101,14 +101,3 @@ jobs: - name: 🏃 Run test suite working-directory: build run: ctest --build-config ${{ matrix.build_type }} - - - name: 📊 Generate coverage reports - if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' - uses: threeal/gcovr-action@v1.0.0 - - - name: ☂️ Upload coverage reports to Codecov - uses: codecov/codecov-action@v3 - if: matrix.os == 'ubuntu-latest' && matrix.c_compiler == 'gcc' - env: - CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} - diff --git a/.github/workflows/coverage.yaml b/.github/workflows/coverage.yaml new file mode 100644 index 0000000..d4f00ee --- /dev/null +++ b/.github/workflows/coverage.yaml @@ -0,0 +1,66 @@ +name: Coverage + +on: + # Triggers the workflow on push or pull request events but only for the "master" branch + push: + branches: + - "master" + pull_request: + branches: + - "master" + +jobs: + build: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v3 + + - name: 🔧 Install GCC + uses: egor-tensin/setup-gcc@v1.3 + with: + version: 13 + + - name: 🔧 Setup python + uses: actions/setup-python@v4 + with: + python-version: '3.10' + cache: pip + + - name: ☁️ Install required packages + run: | + sudo apt-get install -y lcov + pip install -r requirements.txt + + - name: 🐸 Create default Conan profile + run: conan profile detect + + - name: ☁️ Get dependencies + run: conan install ${{ github.workspace }} --build=missing --output-folder=build --settings compiler.cppstd=20 + + - name: 🛠️ Configure CMake + run: > + cmake -B build + -DCMAKE_BUILD_TYPE=Release + -DBUILD_TESTING=ON + -DCODE_COVERAGE=ON + --toolchain=conan_toolchain.cmake + -S ${{ github.workspace }} + + - name: 🔨 Build project + run: cmake --build build --config Release --parallel + + - name: 🏃 Run test suite + working-directory: build + run: ctest --build-config Release + + - name: 📊 Generate coverage reports with lcov + run: | + lcov --directory . --capture --output-file coverage.info + lcov --remove coverage.info '/usr/*' --remove coverage.info '**/.conan*' --remove coverage.info '**/test*' --output-file coverage.info + lcov --list coverage.info + + - name: ☂️ Upload coverage reports to Codecov + uses: codecov/codecov-action@v3 + env: + CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} From 271c55ff8f3bc4bf59e13e5257c3e3c72cacaa99 Mon Sep 17 00:00:00 2001 From: Master92 Date: Mon, 4 Dec 2023 11:01:03 +0100 Subject: [PATCH 10/11] Specify gcov-13 as the gcov tool --- .github/workflows/coverage.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/coverage.yaml b/.github/workflows/coverage.yaml index d4f00ee..6302260 100644 --- a/.github/workflows/coverage.yaml +++ b/.github/workflows/coverage.yaml @@ -56,7 +56,7 @@ jobs: - name: 📊 Generate coverage reports with lcov run: | - lcov --directory . --capture --output-file coverage.info + lcov --directory . --capture --output-file coverage.info --gcov-tool gcov-13 lcov --remove coverage.info '/usr/*' --remove coverage.info '**/.conan*' --remove coverage.info '**/test*' --output-file coverage.info lcov --list coverage.info From d70825fa9eff37524af1765a1602b5a13b628d49 Mon Sep 17 00:00:00 2001 From: Master92 Date: Mon, 4 Dec 2023 13:04:35 +0100 Subject: [PATCH 11/11] Fix library path for MSVC --- tests/CMakeLists.txt | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index ab235f1..4c78aa1 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -29,5 +29,13 @@ if(NOT DOCTEST_CMAKE) message(FATAL_ERROR "Could not find doctest.cmake") else() include(${DOCTEST_CMAKE}) - doctest_discover_tests(${PROJECT_NAME}_tests WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/../src) + set(LIBRARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/../src) + # Fix path for MSVC is located in the respective build type subdirectory + if(MSVC) + set(DOCTEST_CMAKE_DIR "${LIBRARY_DIR}/$") + else() + set(DOCTEST_CMAKE_DIR "${LIBRARY_DIR}") + endif() + + doctest_discover_tests(${PROJECT_NAME}_tests WORKING_DIRECTORY ${DOCTEST_CMAKE_DIR}) endif()