From 80b3544d9bdc2b332e489808a67dfc351a6936e6 Mon Sep 17 00:00:00 2001 From: Egbert Bouman Date: Thu, 7 Mar 2024 15:49:39 +0100 Subject: [PATCH] Added workflow for generating code coverage reports --- .github/actions/coverage/action.yml | 22 ++++++++++++ .github/workflows/coverage.yml | 53 +++++++++++++++++++++++++++++ .github/workflows/unittests.yml | 6 ++-- create_test_coverage_report.py | 11 +++++- 4 files changed, 88 insertions(+), 4 deletions(-) create mode 100644 .github/actions/coverage/action.yml create mode 100644 .github/workflows/coverage.yml diff --git a/.github/actions/coverage/action.yml b/.github/actions/coverage/action.yml new file mode 100644 index 000000000..4af95d2a5 --- /dev/null +++ b/.github/actions/coverage/action.yml @@ -0,0 +1,22 @@ +name: 'Generate coverage report' +inputs: + html_report_name: + description: 'Artifact name for storing HTML coverage report. When omitted no report is stored.' + required: false +runs: + using: "composite" + steps: + - name: Generate coverage report + shell: bash + run: | + pip install coverage + python create_test_coverage_report.py + echo -e "
Coverage report\n" >> $GITHUB_STEP_SUMMARY + cat coverage.md >> $GITHUB_STEP_SUMMARY + echo '
' >> $GITHUB_STEP_SUMMARY + - name: Upload coverage report + if: ${{ inputs.html_report_name }} + uses: actions/upload-artifact@v4 + with: + name: ${{ inputs.html_report_name }} + path: coverage/ diff --git a/.github/workflows/coverage.yml b/.github/workflows/coverage.yml new file mode 100644 index 000000000..95d0b5f7f --- /dev/null +++ b/.github/workflows/coverage.yml @@ -0,0 +1,53 @@ +name: Coverage +on: + push: + branches: + - master + workflow_dispatch: +jobs: + linux: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-python@v5 + with: + python-version: '3.7' + cache: 'pip' + - run: python -m pip install -r requirements.txt + - uses: ./.github/actions/coverage + with: + html_report_name: coverage-linux + windows: + runs-on: windows-latest + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-python@v5 + with: + python-version: '3.8' + cache: 'pip' + - uses: actions/cache/restore@v4 + id: restore_cache + with: + path: libsodium.dll + key: cache_libsodium_dll + - run: python -m pip install -r requirements.txt + - uses: ./.github/actions/coverage + with: + html_report_name: coverage-windows + - uses: actions/cache/save@v4 + if: steps.restore_cache.outputs.cache-hit != 'true' + with: + path: libsodium.dll + key: cache_libsodium_dll + macos: + runs-on: macos-latest + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-python@v5 + with: + python-version: '3.12' + cache: 'pip' + - run: python -m pip install -r requirements.txt + - uses: ./.github/actions/coverage + with: + html_report_name: coverage-macos diff --git a/.github/workflows/unittests.yml b/.github/workflows/unittests.yml index d51b27279..c2954538a 100644 --- a/.github/workflows/unittests.yml +++ b/.github/workflows/unittests.yml @@ -20,7 +20,7 @@ jobs: with: python-version: '3.8' cache: 'pip' - - uses: actions/cache/restore@v3 + - uses: actions/cache/restore@v4 id: restore_cache with: path: libsodium.dll @@ -28,8 +28,8 @@ jobs: - run: python -m pip install -r requirements.txt - name: Run unit tests run: python run_all_tests.py -a - - uses: actions/cache/save@v3 - id: save_cache + - uses: actions/cache/save@v4 + if: steps.restore_cache.outputs.cache-hit != 'true' with: path: libsodium.dll key: cache_libsodium_dll diff --git a/create_test_coverage_report.py b/create_test_coverage_report.py index 0bddc526f..365e00be0 100644 --- a/create_test_coverage_report.py +++ b/create_test_coverage_report.py @@ -1,6 +1,7 @@ import logging import os import pathlib +import platform import shutil import sys from io import StringIO @@ -13,12 +14,16 @@ from coverage.results import Analysis from packaging.version import Version -from run_all_tests import find_all_test_class_names +from run_all_tests import find_all_test_class_names, install_libsodium, windows_missing_libsodium if __name__ != '__main__': print(__file__, "should be run stand-alone! Instead, it is being imported!", file=sys.stderr) # noqa: T201 sys.exit(1) +if platform.system() == 'Windows' and windows_missing_libsodium(): + print("Failed to locate libsodium (libnacl requirement), downloading latest dll!") # noqa: T201 + install_libsodium() + data_file = os.path.join('coverage', 'raw', 'coverage_file') logging.basicConfig(level=logging.CRITICAL) logging.disable(logging.CRITICAL) @@ -71,6 +76,10 @@ def clean_directory(prepare: bool = False) -> None: print("Generating HTML report") # noqa: T201 cov.html_report(directory='coverage') +print("Generating markdown report") # noqa: T201 +with open('coverage.md', 'w') as fp: + cov.report(output_format='markdown', file=fp, show_missing=True) + print("Aggregating package stats") # noqa: T201 total_numbers = {} # Package name -> (Numbers: package coverage stats, dict: files per coverage bin) for filename in cov.get_data().measured_files():