enprot 0.5.78

Engyon Protected Text (EPT) — confidentiality processor and capability ledger
name: benchmark-comparison

# Competitive benchmark: enprot vs SOPS vs git-crypt (the committed-
# ciphertext incumbents). Runs weekly and on demand — NOT per-PR —
# because competitor installs and multi-megabyte corpora are pure
# maintenance cost on every push. Results land as a workflow artifact
# and in the job summary; docs/src/pages/docs/reference/benchmarks.md
# carries the methodology and the current snapshot.
on:
  schedule:
    - cron: "0 5 * * 1"
  workflow_dispatch:

permissions:
  contents: read

env:
  SOPS_VERSION: "3.10.2"
  AGE_VERSION: "1.2.1"

jobs:
  compare:
    runs-on: ubuntu-latest
    timeout-minutes: 45
    permissions:
      contents: write
      pull-requests: write
    steps:
      - uses: actions/checkout@v7

      - uses: dtolnay/rust-toolchain@stable

      - name: Install competitors
        run: |
          set -euxo pipefail
          sudo apt-get -y update && sudo apt-get -y install git-crypt
          curl -fsSL "https://github.com/getsops/sops/releases/download/v${SOPS_VERSION}/sops-v${SOPS_VERSION}.linux.amd64" \
            -o /usr/local/bin/sops && chmod +x /usr/local/bin/sops
          curl -fsSL "https://github.com/FiloSottile/age/releases/download/v${AGE_VERSION}/age-v${AGE_VERSION}-linux-amd64.tar.gz" \
            | tar xz -C /tmp
          # The archive's top-level directory name varies across
          # releases; locate the binaries instead of guessing paths.
          sudo find /tmp -maxdepth 3 -type f \( -name age -o -name age-keygen \) \
            -exec mv {} /usr/local/bin/ \;
          sops --version && age-keygen --version && git-crypt version

      - name: Install C dependencies
        # The same path the tests matrix uses: Botan + librnp from
        # source into /usr/local (bare runners ship neither).
        env:
          BOTAN_VERSION: "3.7.0"
          PREFIX: /usr/local
        run: ./ci/install.sh

      - name: Build enprot
        env:
          PKG_CONFIG_PATH: /usr/local/lib/pkgconfig
        run: cargo build --release --features cli && sudo cp target/release/enprot /usr/local/bin/

      - name: Run comparison harness
        env:
          OUT_DIR: bench-results
        run: ./ci/bench/competitors.sh

      - name: Job summary
        run: cat bench-results/results.jsonl >> "$GITHUB_STEP_SUMMARY"

      - uses: actions/upload-artifact@v7
        with:
          name: benchmark-comparison
          path: bench-results/
          retention-days: 90

      # The snapshot maintains itself: regenerate the docs table from
      # this run's numbers and open a PR when it changed. The table
      # block between the markers is generated; prose stays hand-edit.
      - name: Refresh docs snapshot
        run: |
          ./ci/bench/snapshot.sh docs/src/pages/docs/reference/benchmarks.md bench-results/results.jsonl
          if git diff --quiet -- docs/src/pages/docs/reference/benchmarks.md; then
            echo "snapshot unchanged"; exit 0
          fi
          BR=bench/snapshot-$(date +%Y%m%d)
          git config user.name "enprot-benchmark-bot"
          git config user.email "actions@users.noreply.github.com"
          git checkout -b "$BR"
          git add docs/src/pages/docs/reference/benchmarks.md
          git commit -m "docs(bench): snapshot refresh $(date +%F) — generated from this week's run"
          git push origin "$BR"
          gh pr create --head "$BR" --title "docs(bench): weekly snapshot refresh" \
            --body "Generated by the benchmark-comparison run from its own results.jsonl (ci/bench/snapshot.sh). Numbers-only; review the deltas." || true