Skip to content

GitHub Action pin audit

This page documents .github/workflows/action-pin-audit.yml and tools/ci/audit_action_pins.py.

TopMark includes a dedicated maintenance workflow and repository tool for auditing GitHub Action version pin consistency across workflow files and local composite actions before the stable release path depends on them.

Note

The canonical vocabulary used throughout the documentation is defined in Terminology and Canonical Vocabulary.

Purpose

The GitHub Action pin audit validates that repeated external GitHub Actions use a consistent pinned ref across workflow files and local composite actions.

The audit exists because Dependabot updates workflow files under:

.github/workflows/

but does not reliably track nested local composite-action metadata under:

.github/actions/**/action.yml

Without an additional audit layer, repositories using local composite actions can drift toward inconsistent external action refs over time.

The audit helps prevent:

  • stale action pins;
  • inconsistent CI environments;
  • accidental divergence after Dependabot updates;
  • hidden maintenance drift inside local actions.

The workflow intentionally complements Dependabot rather than attempting to replace it, keeping manual review and CI validation as the final dependency-governance gate.


Trigger conditions

Trigger When it runs Purpose
schedule Weekly cron run Detect GitHub Action pin drift over time
workflow_dispatch Manual maintainer run Run the audit on demand
pull_request Pull requests affecting workflows, local actions, or the audit tool Detect pin inconsistencies before merge

Pull-request runs are path-filtered so unrelated repository changes do not trigger the audit.

The workflow monitors:

.github/workflows/**
.github/actions/**
tools/ci/audit_action_pins.py

Permissions and trust boundary

The workflow uses read-only repository permissions:

permissions:
  contents: read

The workflow intentionally operates as:

  • read-only;
  • non-mutating;
  • offline;
  • low-privilege.

The audit does not:

  • publish packages;
  • upload artifacts;
  • modify repository files;
  • query GitHub APIs;
  • update dependencies automatically.

The audit performs static repository analysis only.


Jobs and validation scope

Job Purpose Main tools
audit-action-pins Detect divergent GitHub Action refs across workflows and local composite actions python, tools/ci/audit_action_pins.py

The workflow currently consists of a single lightweight audit job running on:

runs-on: ubuntu-latest

The job:

  1. checks out the repository;
  2. runs the audit tool;
  3. fails if repeated actions use inconsistent refs.

The workflow intentionally avoids network access or dependency-resolution logic beyond the standard runner environment.


Artifact handling

This workflow does not produce, consume, or publish build or release artifacts.

The audit validates repository consistency only and does not participate in package publication, release artifact validation, or published artifact validation.


Local reproduction

Run the default repository consistency audit:

python tools/ci/audit_action_pins.py

Print an aggregated summary report:

python tools/ci/audit_action_pins.py --report summary

Print refs grouped by source file:

python tools/ci/audit_action_pins.py --report files

Print both reports:

python tools/ci/audit_action_pins.py --report all

The default command exits with:

Exit code Meaning
0 All repeated actions use consistent refs
1 Divergent refs were detected

Example successful output:

GitHub Actions pin audit
========================

External action references scanned: 25

OK: all repeated external actions use consistent refs.

Maintenance notes

TopMark pins GitHub Actions to full commit SHAs for reproducibility and supply-chain hardening.

Example:

uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

The SHA is the actual execution target. The trailing version comment is retained only for human readability and maintenance review.

When updating pinned GitHub Actions for the stable release workflow set:

  1. update workflow files;
  2. update local composite actions;
  3. run the audit locally;
  4. ensure the workflow remains green.

The audit tool scans:

.github/workflows/**/*.yml
.github/workflows/**/*.yaml
.github/actions/**/action.yml
.github/actions/**/action.yaml

and extracts external action references of the form:

uses: owner/repo@ref

Local actions such as:

uses: ./.github/actions/setup-python-nox

are intentionally ignored because the audit is concerned with external dependency pinning.

The tool intentionally does not:

  • query GitHub APIs;
  • auto-upgrade actions;
  • mutate workflow files;
  • resolve tags dynamically;
  • replace Dependabot.

This keeps the audit deterministic, offline, reproducible, and lightweight enough for routine CI usage.