Skip to content
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
71 changes: 71 additions & 0 deletions standards/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,10 @@
# 3. The job name `build-and-test` is the required CI status check. Keep it — or,
# if you split into per-language jobs (e.g. TypeScript, Go, Python), update the
# repo's branch-protection required checks to match the new job names.
# 4. Two more jobs ship by default and are org required checks — `Secret scan
# (gitleaks)` (per push-protection.md; needs a .gitleaks.toml at root, seeded
# with this template) and `coverage` (green until your stack emits coverage).
Comment thread
don-petry marked this conversation as resolved.
Resolved
# Keep their job names stable so the required checks stay satisfied.
#
# CONVENTIONS (enforced by the standard):
# • permissions: {} at top, least-privilege per job (CI needs contents: read)
Expand Down Expand Up @@ -51,3 +55,70 @@ jobs:
# placeholder below keeps the required `build-and-test` check green.
- name: Placeholder — replace with real build/test steps
run: echo "CI stub — add your stack's lint/format/typecheck/test/coverage steps; see BOOTSTRAP.md."

# Canonical secret-scan job — copied verbatim from push-protection.md#required-ci-job.
# Produces the `Secret scan (gitleaks)` required check. Uses the gitleaks CLI (not
# gitleaks/gitleaks-action, whose v2+ needs a paid org license); fully pinned +
# checksum-verified; no SARIF upload, so no `security-events: write` permission.
secret-scan:
name: Secret scan (gitleaks)
runs-on: ubuntu-latest
permissions:
contents: read
steps:
- name: Checkout (full history)
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 0

- name: Install gitleaks
env:
GITLEAKS_VERSION: "8.30.1"
# Named GITLEAKS_CHECKSUM (not GITLEAKS_SHA256) — SonarCloud flags env var names
# matching *SHA256* containing hex strings as Security Hotspots (false positive).
GITLEAKS_CHECKSUM: "551f6fc83ea457d62a0d98237cbad105af8d557003051f41f3e7ca7b3f2470eb"
run: |
tarball="gitleaks_${GITLEAKS_VERSION}_linux_x64.tar.gz"
url="https://github.com/gitleaks/gitleaks/releases/download/v${GITLEAKS_VERSION}/${tarball}"
wget -q "${url}" -O /tmp/gitleaks.tar.gz
echo "${GITLEAKS_CHECKSUM} /tmp/gitleaks.tar.gz" | sha256sum -c
tar -xzf /tmp/gitleaks.tar.gz -C /usr/local/bin gitleaks
Comment thread
don-petry marked this conversation as resolved.
Resolved

- name: Run gitleaks
# Requires a .gitleaks.toml at repo root (seeded by seed-repo-template.sh).
run: gitleaks detect --source . --config .gitleaks.toml --redact --verbose --exit-code 1

# Stack-aware coverage — produces the `coverage` required check. Default stack is
# shell/bats via kcov. GREEN-UNTIL-TESTS: when a stack emits no coverage yet, the
# job succeeds without producing a report, so seeding it fleet-wide never bricks a
# repo that has no test suite. It begins enforcing once tests exist. Add a per-stack
# block below (keep the job id and `name:` as `coverage` so the required check is stable).
coverage:
name: coverage
runs-on: ubuntu-latest
permissions:
contents: read
steps:
- name: Checkout repository
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

- name: Coverage (shell/bats via kcov)
run: |
shopt -s globstar nullglob
bats_files=(tests/**/*.bats)
if [ ${#bats_files[@]} -eq 0 ]; then
echo "No bats tests found — coverage is green until tests exist."
exit 0
fi
sudo apt-get update -qq
sudo apt-get install -y -qq bats kcov
mkdir -p coverage
kcov --include-path=. --exclude-path=tests,coverage coverage bats "${bats_files[@]}"
echo "Coverage report written to ./coverage"

# ── Per-stack expansion — replace/augment the shell block above for your stack.
# Keep the job id and `name:` as `coverage` so the required check is unchanged.
# Node: npx jest --coverage
# Go: go test ./... -coverprofile=coverage.out && go tool cover -func=coverage.out
# Python: pytest --cov
# Rust: cargo llvm-cov --workspace
Loading