Skip to content

Hypatia scanner build-cache is stale-by-design — merged scanner fixes never activate in CI #437

Description

@hyperpolymath

Problem (root cause, found during the scan-triage session 2026-06-27)

.github/workflows/hypatia-scan-reusable.yml caches the entire built scanner and never rebuilds it:

- uses: actions/cache@...
  with:
    path: |
      ~/.mix
      ~/.hex
      ~/hypatia          # <- the cloned + built scanner
    key: hypatia-scanner-v2-${{ runner.os }}-build   # <- STATIC key
- name: Clone Hypatia
  run: if [ ! -d "$HOME/hypatia" ]; then git clone --depth 1 .../hypatia.git "$HOME/hypatia"; fi
- name: Build Hypatia scanner
  run: cd "$HOME/hypatia"; if [ ! -x hypatia ]; then mix deps.get && mix escript.build; fi

Because the key is static and the clone/build steps are guarded by existence checks, once the cache exists every scan restores the old ~/hypatia and never refreshes it. Any change merged to the hypatia scanner (rules, suppression, CLI) stays inert in CI until the cache is manually busted — confirmed: the Build Hypatia scanner step runs in 0s (cache hit) on every run, and PR #543's SD022 fix did not change the self-scan count on the PR that introduced it.

Estate-wide impact: every repo's scan is frozen on whatever scanner version was first cached.

Interim unblock (per scanning repo)

gh cache delete hypatia-scanner-v2-Linux-build --repo hyperpolymath/hypatia

Next scan rebuilds from main. (Repeat per repo, or let caches age out.)

Durable fix (this issue)

Key the cache on hypatia's current main commit so it auto-busts on every scanner change. Resolve the SHA in a prior step and use it in the key:

- id: hyp
  run: echo "sha=$(git ls-remote https://github.com/hyperpolymath/hypatia.git refs/heads/main | cut -f1)" >> "$GITHUB_OUTPUT"
- uses: actions/cache@...
  with:
    path: [ ~/.mix, ~/.hex, ~/hypatia ]
    key: hypatia-scanner-v3-${{ runner.os }}-${{ steps.hyp.outputs.sha }}

(No restore-keys prefix-match for ~/hypatia, or a stale tree gets restored for a new SHA. Worst-case degradation is "always rebuild," which is correct, not broken.)

Follow-up after merge (separate, blocked on this)

  • Re-pin the scan wrappers in hypatia and gitbot-fleet (.github/workflows/hypatia-scan.yml, currently @e2ef79eecdd623ff631fcbf3fe0268ba4f4ce166) to the new standards-main commit.
  • Mind the governance Workflow-Staleness check: pin to an actual ancestor of standards/main (not a squashed PR-head SHA).

Blast radius

Affects the reusable consumed by ~all estate repos → review + a test scan before merging. Left as an issue rather than shipped unsupervised.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions