Skip to content

Pin actions by SHA and drop job permissions to least privilege - #1

Merged
repsecure merged 2 commits into
mainfrom
harden/pin-actions-least-privilege
Aug 5, 2026
Merged

Pin actions by SHA and drop job permissions to least privilege#1
repsecure merged 2 commits into
mainfrom
harden/pin-actions-least-privilege

Conversation

@repsecure

Copy link
Copy Markdown
Owner

Brings this repo to the same workflow supply-chain standard as agentwall.

Every action is now pinned to a full commit SHA with the precise version in a trailing comment. A mutable tag can be repointed at arbitrary code that then runs holding the job's credentials, and softprops/action-gh-release@v2 was running that way in a job with contents: write.

Checkouts set persist-credentials: false, so the token stops living in .git/config for the remainder of the job. Every job declares explicit least-privilege permissions instead of inheriting the repository default.

A workflows job now runs a dependency-free pin checker, so the property is enforced rather than remembered.

Two changes beyond the brief, both worth calling out:

  • The release workflow's single desktop job held contents: write while running npm ci and electron-builder across three operating systems. Permissions are per-job, so it is split into desktop (build and upload artifacts, contents: read) and release (attach them, contents: write). It reuses artifacts the workflow already uploaded, and if-no-files-found: error prevents the split from producing an empty release.
  • GH_TOKEN was removed from the build step. All three dist scripts pass --publish never, so electron-builder has nothing to publish, and a token there is readable by every process the build spawns.

scripts/check.sh also runs the pin check now, because it promises the same checks as CI and would otherwise have been making a false claim.

`uses: owner/repo@v2` resolves a mutable git ref when the job starts. Whoever
owns that repository can repoint the tag at any commit, and the next run
executes it with this workflow's GITHUB_TOKEN. What this repository ships is
provisioning scripts a reader runs as root on their own hardware, so an action
that changes under its tag can alter what a reader is told to execute. Both
references now name a 40-character commit SHA with a trailing version comment,
so the code reviewed is the code that runs and a reader can still see which
release a SHA is.

Both checkouts set persist-credentials: false. The default leaves the job token
in .git/config, where any later step, including the link checker's own tooling,
can read it and act as this workflow.

Each job declares contents: read rather than inheriting the repository default,
which on many repositories is read-write.

scripts/check-workflow-pins.js enforces both properties on every push and pull
request, so a pin that decays back to a tag fails the build instead of passing
review as an ordinary line in a diff. It is stdlib-only and reads no YAML: a
guard on the supply chain that runs third-party code to do its job has moved the
problem rather than solved it. scripts/check.sh runs it too, because that script
promises the same checks as CI and a pin is cheaper to fix before the push.
CI's Shellcheck step has failed on every run since 2026-07-03. Both hits are
SC2034 on `for i in $(seq 1 N)` retry loops where the counter is genuinely
unused, which is idiomatic; the underscore is shellcheck's own convention for
a variable that exists only to make the loop repeat.

A lint gate that is permanently red teaches everyone to ignore it, which costs
more than the warnings it reports.

Signed-off-by: reesebuilt <126643625+reesepj@users.noreply.github.com>
@repsecure
repsecure force-pushed the harden/pin-actions-least-privilege branch from 6d04834 to 0a3ba1e Compare August 5, 2026 15:54
@repsecure
repsecure merged commit 9c97e4f into main Aug 5, 2026
4 checks passed
repsecure added a commit that referenced this pull request Aug 5, 2026
Pin actions by SHA and drop job permissions to least privilege
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant