release: crumble-v4.7.0 #120
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: CI (build) | |
| on: | |
| push: | |
| branches: [main] | |
| pull_request: | |
| permissions: | |
| contents: read | |
| jobs: | |
| clang-format: | |
| runs-on: ubuntu-latest | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: recursive | |
| # Full history so we can diff changed files against the base commit. | |
| fetch-depth: 0 | |
| - uses: actions/setup-python@v6 | |
| with: | |
| python-version: "3.14" | |
| - name: Install clang-format-21 | |
| run: | | |
| wget https://apt.llvm.org/llvm.sh | |
| chmod +x llvm.sh | |
| sudo ./llvm.sh 21 | |
| sudo apt-get update | |
| sudo apt-get install -y clang-format-21 | |
| # Check only the lines changed by this push/PR, not the whole repo. The | |
| # tree carries pre-existing formatting that predates this gate and is | |
| # shared with upstream CrossInk; reformatting it wholesale would churn | |
| # ~35 files and conflict on every upstream sync. git-clang-format limits | |
| # the check to changed hunks so new code stays clean without that churn. | |
| - name: Run clang-format on changed lines | |
| run: | | |
| set -euo pipefail | |
| if [ "${{ github.event_name }}" = "pull_request" ]; then | |
| git fetch --no-tags origin "${{ github.base_ref }}" | |
| BASE="origin/${{ github.base_ref }}" | |
| else | |
| BASE="${{ github.event.before }}" | |
| fi | |
| if ! git rev-parse --verify --quiet "${BASE}^{commit}" >/dev/null; then | |
| BASE="$(git rev-parse HEAD^ 2>/dev/null || git hash-object -t tree /dev/null)" | |
| fi | |
| echo "Checking changed lines against ${BASE}" | |
| DIFF="$(PATH=/usr/lib/llvm-21/bin:$PATH git-clang-format --binary clang-format-21 --diff "${BASE}" -- '*.c' '*.cpp' '*.h' '*.hpp' || true)" | |
| if [ -z "${DIFF}" ] || echo "${DIFF}" | grep -qE "^(no modified files to format|clang-format did not modify any files)$"; then | |
| echo "Changed lines are clang-format clean." | |
| exit 0 | |
| fi | |
| echo "${DIFF}" | |
| echo "Changed lines need formatting. Run: git-clang-format ${BASE}" | |
| exit 1 | |
| cppcheck: | |
| runs-on: ubuntu-latest | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: recursive | |
| - uses: actions/setup-python@v6 | |
| with: | |
| python-version: "3.14" | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v7 | |
| with: | |
| version: "latest" | |
| enable-cache: true | |
| - name: Cache PlatformIO packages | |
| uses: actions/cache@v4 | |
| with: | |
| path: ~/.platformio | |
| key: ${{ runner.os }}-platformio-${{ hashFiles('platformio.ini', 'platformio.local.example.ini') }} | |
| restore-keys: | | |
| ${{ runner.os }}-platformio- | |
| - name: Install PlatformIO Core | |
| run: uv pip install --system -U https://github.com/pioarduino/platformio-core/archive/refs/tags/v6.1.19.zip | |
| # Fail only on medium/high defects (real bugs). The low-severity "style" | |
| # bucket (useStlAlgorithm, variableScope, etc.) is advisory and noisy on | |
| # the existing tree; gating on it blocked CI without catching real issues. | |
| - name: Run cppcheck | |
| run: pio check --fail-on-defect medium --fail-on-defect high | |
| build: | |
| runs-on: ubuntu-latest | |
| steps: | |
| - uses: actions/checkout@v6 | |
| with: | |
| submodules: recursive | |
| - uses: actions/setup-python@v6 | |
| with: | |
| python-version: "3.14" | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v7 | |
| with: | |
| version: "latest" | |
| enable-cache: true | |
| - name: Cache PlatformIO packages | |
| uses: actions/cache@v4 | |
| with: | |
| path: ~/.platformio | |
| key: ${{ runner.os }}-platformio-${{ hashFiles('platformio.ini', 'platformio.local.example.ini') }} | |
| restore-keys: | | |
| ${{ runner.os }}-platformio- | |
| - name: Install PlatformIO Core | |
| run: uv pip install --system -U https://github.com/pioarduino/platformio-core/archive/refs/tags/v6.1.19.zip | |
| - name: Build CrossInk | |
| run: | | |
| set -euo pipefail | |
| pio run | tee pio.log | |
| - name: Extract firmware stats | |
| run: | | |
| set -euo pipefail | |
| { | |
| echo "## Firmware build stats" | |
| grep -E "RAM:\s|Flash:\s" pio.log | while read -r line; do echo "- ${line}"; done | |
| } >> "$GITHUB_STEP_SUMMARY" | |
| - name: Upload firmware artifacts | |
| uses: actions/upload-artifact@v7 | |
| with: | |
| name: firmware | |
| path: | | |
| .pio/build/teensy/firmware-teensy.bin | |
| .pio/build/tiny/firmware-tiny.bin | |
| .pio/build/xlarge/firmware-xlarge.bin | |
| .pio/build/no_emoji/firmware-no_emoji.bin | |
| if-no-files-found: error | |
| # This job is used as the PR required actions check, allows for changes to other steps in the future without breaking | |
| # PR requirements. | |
| test-status: | |
| name: Test Status | |
| needs: | |
| - build | |
| - clang-format | |
| - cppcheck | |
| if: always() | |
| runs-on: ubuntu-latest | |
| steps: | |
| - name: Fail because needed jobs failed | |
| # Fail if any job failed or was cancelled (skipped jobs are ok) | |
| if: ${{ contains(needs.*.result, 'failure') || contains(needs.*.result, 'cancelled') }} | |
| run: exit 1 | |
| - name: Success | |
| run: exit 0 |