Nearly every consumer re-pin of review-reusable.yml was a reviewer IMAGE bump, not a structural change — but the tag was baked into a `uses: docker://` step, which is parsed before any expression context exists and so can't read a variable. Run the reviewer as the JOB container instead (container.image DOES accept expressions) with an explicit `run: /entrypoint.sh` step: the tag now resolves per-run via inputs.reviewer_tag → user var GADFLY_REVIEWER_TAG → the baked fallback pin (sha-b37cd09, unchanged). A Gadfly release becomes: build the image, update the ONE user-level variable — every consumer pinned to this file's @<sha> picks it up on its next review with no re-pin. Workflow re-pins remain only for structural yml changes (this is one — intended to be the last routine one). - Entrypoint contract unchanged: same env block, same /entrypoint.sh brains (bash + entrypoint already live in the image; ENTRYPOINT was /entrypoint.sh). - Keep the variable on immutable sha- tags, never :latest (act_runner caches :latest and often does not re-pull a moved one). - Tradeoff noted in comments: vars are unmasked and move without a commit trail — same blast radius as editing this file, minus the audit trail. - README (image/pinning para + Central config table) and examples/reusable.yml updated per the maintenance rule. Co-Authored-By: Claude Fable 5 <[email protected]>