Skip to content

SonarCloud: GitHub Actions / dependency hardening (×11) #303

Closed

Description

@don-petry

GitHub Actions / dependency supply-chain hardening

SonarCloud open findings in petry-projects/markets — 11 issue(s) grouped as one workstream. Part of the org SonarCloud tuning initiative combsmith/.github#593.

Findings

Rule Count Representative message
githubactions:S6505 6 Omitting "--ignore-scripts" allows lifecycle scripts to run during package installation.
githubactions:S8543 5 Define exact package version to avoid installing unverified releases.

Affected files

  • .github/workflows/ci.yml (11)

Approach

Harden workflow/package steps: pin exact versions, add --ignore-scripts/--only-binary, use lockfile-enforcing install commands. Where a step comes from a shared .github reusable, fix it at the source so callers inherit.

Acceptance

  • All listed SonarCloud findings for this repo/workstream resolved to zero
  • No behavior change; existing tests/CI green
  • Fixes are real (no blanket NOSONAR unless a confirmed false positive, noted inline)

Filed from the 2026-07-03 org SonarCloud review.

Activity

  1. don-petry commented on Jul 3, 2026

    @don-petry
    ContributorAuthor

    Dev-Lead Implementation Plan

    Issue: #303 — SonarCloud: GitHub Actions / dependency hardening (×11)

    Scope

    Harden the npm/npx steps in .github/workflows/ci.yml to resolve 6× githubactions:S6505 (missing --ignore-scripts) and 5× githubactions:S8543 (unpinned package version) with no behavior change.

    Root-cause mapping (11 findings, all in ci.yml)

    • S6505 ×6 — npm ci (1) + 5 npx calls all omit --ignore-scripts, so lifecycle scripts may run during install.
    • S8543 ×5 — the 5 npx calls (tsc, eslint, prettier, graphql-codegen, jest) don't pin an exact version, so npx could install an unverified release.

    Implementation Checklist

    • npm ci → npm ci --ignore-scripts (S6505)
    • npx tsc --noEmit → npx --no-install --ignore-scripts tsc --noEmit (S6505 + S8543)
    • npx eslint … → npx --no-install --ignore-scripts eslint …
    • npx prettier --check . → npx --no-install --ignore-scripts prettier --check .
    • npx graphql-codegen --check → npx --no-install --ignore-scripts graphql-codegen --check
    • npx jest … → npx --no-install --ignore-scripts jest …

    --no-install forces npx to use the exact, lockfile-pinned binaries already installed by npm ci (satisfying S8543 without duplicating versions in the workflow), and --ignore-scripts disables lifecycle scripts (S6505). Both are behavior-preserving: local bins already took precedence at runtime.

    Tests to Write

    • None. This is a behavior-preserving GitHub Actions config change (no package.json/go.mod yet exists in the repo, so these steps are currently dormant). Per the dev-lead Phase 2 exception for config/behavior-preserving changes, no unit tests apply. Verification is via YAML validity + .dev-lead/scripts/dev-lead-lint.sh.

    Test Command

    bash ".dev-lead/scripts/dev-lead-lint.sh" (plus python3 -c 'import yaml; yaml.safe_load(open(".github/workflows/ci.yml"))' for YAML sanity)

  2. don-petry commented on Jul 3, 2026

    @don-petry
    ContributorAuthor

    Dev-Lead: Implementation Complete

    Plan Execution

    • npm ci → npm ci --ignore-scripts (S6505)
    • npx tsc → npx --no-install --ignore-scripts tsc --noEmit (S6505 + S8543)
    • npx eslint → npx --no-install --ignore-scripts eslint . --max-warnings 0
    • npx prettier → npx --no-install --ignore-scripts prettier --check .
    • npx graphql-codegen → npx --no-install --ignore-scripts graphql-codegen --check
    • npx jest → npx --no-install --ignore-scripts jest --ci --coverage …

    All 11 findings addressed with real fixes (no NOSONAR):

    • S6505 ×6 — --ignore-scripts added to the npm ci install and all 5 npx exec steps, disabling lifecycle scripts.
    • S8543 ×5 — --no-install on each npx forces use of the exact, lockfile-pinned binary installed by npm ci instead of fetching an unverified release from the registry. No versions are duplicated into the workflow (they stay single-sourced in package-lock.json).

    Test Results

    === YAML sanity ===
    ci.yml: valid YAML
    === dev-lead lint ===
      [lint] shellcheck: no .sh files found — skipping
      [lint] validating CODEOWNERS...
    OK: CODEOWNERS
      [lint] all checks passed
    lint exit: 0
    

    TDD note (Phase 2 exception): This is a behavior-preserving GitHub Actions config change. The repo currently has no package.json/go.mod, so the frontend/backend jobs are skipped by the detect gate and these steps are dormant — there is no runtime behavior to unit-test. Verification was YAML validity + the required repo lint. The changes are also behavior-preserving at runtime: npx already preferred the locally-installed bins, and --ignore-scripts matches the org canonical pattern in copilot-setup-steps.yml.

    Files Changed

    • .github/workflows/ci.yml: hardened the 6 npm/npx steps in the frontend job with --ignore-scripts (all 6) and --no-install (the 5 npx calls).

    Notes

    • npm ci --ignore-scripts matches the org-standard pattern already documented in .github/workflows/copilot-setup-steps.yml:92, so no new convention is introduced.
    • --no-install will cause an npx step to fail fast if a tool is ever removed from devDependencies — desirable, since it surfaces an undeclared dependency rather than silently pulling one from the registry.
    • Non-npm steps (go run github.com/99designs/gqlgen, gh release download v8.30.1) were left unchanged — they are outside the S6505/S8543 (npm-ecosystem) rule scope and the gitleaks download is already version-pinned with a checksum.
  3. added a commit that references this issue on Jul 11, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    dev-leadFor dev-lead agent pickupenhancementFeature requestssecuritySecurity-related PRs and issues

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions