granite-cli 0.2.3

CLI for discovering, configuring, and launching AI workflows powered by IBM Granite models.
name: CI

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

jobs:
  rust:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout repository
        uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7

      - name: Install Rust toolchain
        uses: dtolnay/rust-toolchain@2c7215f132e9ebf062739d9130488b56d53c060c # 1.96.1
        with:
          toolchain: 1.88.0
          components: rustfmt, clippy

      - name: Cache cargo build artifacts
        uses: Swatinem/rust-cache@c19371144df3bb44fab255c43d04cbc2ab54d1c4 # v2.9.1

      - name: Check formatting
        run: cargo fmt --all -- --check

      - name: Run Clippy
        run: cargo clippy --all-targets --all-features -- -D warnings

      - name: Build
        run: cargo build --locked --all-targets --all-features

      - name: Test
        run: cargo test --locked --all-targets --all-features

  cross-build:
    name: Build + test (${{ matrix.target }})
    runs-on: ${{ matrix.os }}
    strategy:
      matrix:
        include:
          - target: x86_64-unknown-linux-gnu
            os: ubuntu-latest
          - target: aarch64-unknown-linux-gnu
            os: ubuntu-latest
          - target: aarch64-apple-darwin
            os: macos-latest
          - target: x86_64-pc-windows-msvc
            os: windows-latest
          # DISABLED: These runners seem to be unavailable on GitHub Actions,
          #   so they block builds
          #- target: x86_64-apple-darwin
          #  os: macos-13

    steps:
      - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7

      - uses: dtolnay/rust-toolchain@2c7215f132e9ebf062739d9130488b56d53c060c # 1.96.1
        with:
          toolchain: 1.88.0
          targets: ${{ matrix.target }}

      - uses: Swatinem/rust-cache@c19371144df3bb44fab255c43d04cbc2ab54d1c4 # v2.9.1
        with:
          key: ${{ matrix.target }}

      - name: Install cross-compilation tools
        if: matrix.target == 'aarch64-unknown-linux-gnu'
        run: |
          sudo apt-get update
          sudo apt-get install -y gcc-aarch64-linux-gnu

      - name: Build
        run: cargo build --locked --release --target ${{ matrix.target }} --all-targets --all-features
        env:
          CARGO_TARGET_AARCH64_UNKNOWN_LINUX_GNU_LINKER: aarch64-linux-gnu-gcc

      - name: Test
        if: matrix.target != 'aarch64-unknown-linux-gnu'
        run: cargo test --locked --target ${{ matrix.target }} --all-targets --all-features

  coverage:
    name: Coverage
    runs-on: ubuntu-latest
    env:
      # Minimum line coverage, in percent: for the whole crate, and for the
      # lines a pull request adds or changes.
      COVERAGE_MIN_TOTAL: "80"
      COVERAGE_MIN_DIFF: "80"
      DIFF_COVER_VERSION: "10.6.0"

    steps:
      - name: Checkout repository
        uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
        with:
          # diff-cover compares against the base branch
          fetch-depth: 0

      - name: Install Rust toolchain
        uses: dtolnay/rust-toolchain@2c7215f132e9ebf062739d9130488b56d53c060c # 1.96.1
        with:
          toolchain: 1.88.0
          components: llvm-tools-preview

      - name: Cache cargo build artifacts
        uses: Swatinem/rust-cache@c19371144df3bb44fab255c43d04cbc2ab54d1c4 # v2.9.1
        with:
          key: coverage

      - name: Install cargo-llvm-cov
        uses: taiki-e/install-action@83ac0ad63c0167e6f06796fab0fce28db1bf3db0 # v2.87.22
        with:
          tool: cargo-llvm-cov@0.9.1

      - name: Test with coverage
        run: cargo llvm-cov --no-report --locked --all-targets --all-features

      - name: Generate reports
        run: |
          cargo llvm-cov report --lcov --output-path lcov.info
          cargo llvm-cov report --html --output-dir coverage
          cargo llvm-cov report --json --summary-only --output-path coverage-summary.json
          lines=$(jq '.data[0].totals.lines.percent' coverage-summary.json)
          printf '## Coverage\n\nLine coverage: **%.2f%%** (minimum %s%%)\n\n' \
            "$lines" "$COVERAGE_MIN_TOTAL" >> "$GITHUB_STEP_SUMMARY"

      - name: Check coverage of changed lines
        if: github.event_name == 'pull_request'
        env:
          BASE_REF: ${{ github.base_ref }}
        run: |
          status=0
          pipx run "diff-cover==${DIFF_COVER_VERSION}" lcov.info \
            --compare-branch="origin/${BASE_REF}" \
            --format markdown:diff-cover.md \
            --fail-under="$COVERAGE_MIN_DIFF" || status=$?
          cat diff-cover.md >> "$GITHUB_STEP_SUMMARY"
          exit "$status"

      - name: Check total coverage
        if: ${{ !cancelled() }}
        run: cargo llvm-cov report --summary-only --fail-under-lines "$COVERAGE_MIN_TOTAL"

      - name: Upload coverage reports
        if: ${{ !cancelled() }}
        uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
        with:
          name: coverage
          path: |
            lcov.info
            coverage/html
            diff-cover.md
          if-no-files-found: ignore