name: CI on: push: branches: [main] pull_request: concurrency: group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true env: # GitHub-hosted runners are Ubuntu 24.04; the project targets 26.04. bootstrap.sh warns # but proceeds. Revisit when 26.04 runners exist. DEBIAN_FRONTEND: noninteractive jobs: # --- fast lint jobs: no compiler, no heavy deps ------------------------------------- clang-format: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Install clang-format run: sudo apt-get update -qq && sudo apt-get install -y --no-install-recommends clang-format - name: Check formatting run: | shopt -s globstar nullglob files=(core/**/*.{cpp,hpp} daemon/**/*.{cpp,hpp} cli/**/*.{cpp,hpp} nmhost/**/*.{cpp,hpp}) if [ ${#files[@]} -eq 0 ]; then echo "no C++ sources yet — skipping"; exit 0; fi printf '%s\n' "${files[@]}" clang-format --dry-run --Werror "${files[@]}" testserver: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - uses: actions/setup-python@v5 with: python-version: '3.12' - name: testserver self-test run: python3 tools/testserver/selftest.py bootstrap-script: # Keeps tools/bootstrap.sh honest: it must run clean and its --check must pass. runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - run: sudo ./tools/bootstrap.sh --with-clang - run: ./tools/bootstrap.sh --check extension-lint: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - id: check run: | if [ -f extension/package.json ]; then echo "present=true" >> "$GITHUB_OUTPUT" else echo "present=false" >> "$GITHUB_OUTPUT"; fi - uses: actions/setup-node@v4 if: steps.check.outputs.present == 'true' with: node-version: '20' - name: web-ext lint if: steps.check.outputs.present == 'true' working-directory: extension run: | npm ci npx web-ext lint --source-dir . - name: skipped if: steps.check.outputs.present == 'false' run: echo "extension/ has not landed yet — skipping web-ext lint" # --- build + test matrix ---------------------------------------------------------- build: runs-on: ubuntu-latest strategy: fail-fast: false matrix: compiler: [gcc, clang] env: CC: ${{ matrix.compiler == 'gcc' && 'gcc' || 'clang' }} CXX: ${{ matrix.compiler == 'gcc' && 'g++' || 'clang++' }} steps: - uses: actions/checkout@v4 - name: Bootstrap toolchain run: sudo ./tools/bootstrap.sh --with-clang - name: Configure run: cmake --preset ci - name: Build run: cmake --build --preset ci - name: Test run: ctest --preset ci --output-on-failure sanitizers: runs-on: ubuntu-latest strategy: fail-fast: false matrix: preset: [dev, tsan] # dev = ASan + UBSan steps: - uses: actions/checkout@v4 - name: Bootstrap toolchain run: sudo ./tools/bootstrap.sh --with-clang - name: Configure run: cmake --preset ${{ matrix.preset }} - name: Build run: cmake --build --preset ${{ matrix.preset }} - name: Test run: ctest --preset ${{ matrix.preset }} --output-on-failure env: ASAN_OPTIONS: detect_leaks=1:halt_on_error=1 UBSAN_OPTIONS: print_stacktrace=1:halt_on_error=1 TSAN_OPTIONS: halt_on_error=1 clang-tidy: # Advisory through M1 (see .clang-tidy WarningsAsErrors: ''); becomes required at M2. runs-on: ubuntu-latest continue-on-error: true steps: - uses: actions/checkout@v4 - id: check run: | if ls core/CMakeLists.txt daemon/CMakeLists.txt >/dev/null 2>&1; then echo "present=true" >> "$GITHUB_OUTPUT" else echo "present=false" >> "$GITHUB_OUTPUT"; fi - name: Bootstrap toolchain if: steps.check.outputs.present == 'true' run: sudo ./tools/bootstrap.sh - name: Configure (for compile_commands.json) if: steps.check.outputs.present == 'true' run: cmake --preset dev - name: Run clang-tidy on changed files if: steps.check.outputs.present == 'true' run: | mapfile -t files < <(git diff --name-only --diff-filter=ACM \ "${{ github.event.pull_request.base.sha || 'HEAD~1' }}" HEAD \ -- '*.cpp' '*.hpp' || true) [ ${#files[@]} -eq 0 ] && { echo "no C++ changes"; exit 0; } printf '%s\n' "${files[@]}" clang-tidy -p build/dev "${files[@]}" - name: skipped if: steps.check.outputs.present == 'false' run: echo "no C++ lane has landed a CMakeLists yet — skipping clang-tidy" conformance: # Required check on every PR once tests/conformance/ lands (branch protection is # configured in the repo settings, not here — see .github/BRANCH_PROTECTION.md). runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - id: check run: | if [ -f tests/conformance/CMakeLists.txt ] || [ -f tests/conformance/package.json ]; then echo "present=true" >> "$GITHUB_OUTPUT" else echo "present=false" >> "$GITHUB_OUTPUT"; fi - name: Bootstrap toolchain if: steps.check.outputs.present == 'true' run: sudo ./tools/bootstrap.sh - name: Run conformance suite if: steps.check.outputs.present == 'true' run: | cmake --preset dev ctest --preset dev --output-on-failure -L conformance - name: skipped if: steps.check.outputs.present == 'false' run: echo "tests/conformance/ has not landed yet — skipping"