<< All versions

Skill v1.0.1

currentLLM-judged scan90/100
babarot/gh-infra/ci-cd

+1 new

──Details
PublishedOctober 16, 2026 at 08:25 PM
Content Hashsha256:3aa6b7dbc649e036...
Git SHA1250b3688391
Bump Typepatch
Compare with v1.0.0
──Files
Files (1 file, 5.1 KB)
SKILL.md5.1 KBactive
SKILL.md · 59 lines · 5.1 KB

version: "1.0.1" name: ci-cd description: > CI/CD integration for gh-infra in GitHub Actions: plan each pull request and post the plan as a comment, apply on merge, scheduled drift detection with notification, --changed-since and --detailed-exitcode, self-managed vs central-management layouts, and which token each needs.


CI/CD Integration

Use this skill when the user wants GitHub Actions workflows around gh-infra.

Recommended Setup

Three workflows; full YAML in references/workflows.md. Copy them and change only the paths and the secret name.

WorkflowTriggerCommand
Plan on pull requestpull_requestgh infra plan <paths> --changed-since origin/${{ github.base_ref }} --detailed-exitcode -o markdown > plan.md, then gh pr comment --body-file plan.md --edit-last --create-if-none
Apply on mergepush to main, workflow_dispatchgh infra apply <paths> --changed-since "$BEFORE" --auto-approve; without --changed-since when github.event.before is empty or all zeros
Drift detectionschedule, workflow_dispatchgh infra plan <paths> --detailed-exitcode -o markdown > plan.md (no --changed-since), notify on exit 2

Optional fourth: pull changes made on GitHub into the manifests on a schedule with gh infra import --into=<path> --auto-approve and open a pull request (also in workflows.md).

Use the three unless the user wants less. Drift detection is also the safety net for apply runs that failed: a failed apply --changed-since is not retried by the next push.

Rules For Every Workflow

  • install the extension: - run: gh extension install babarot/gh-infra after actions/checkout, with GH_TOKEN set at job level
  • pass every manifest directory to one command: gh infra plan ./repos/ ./files/. One exit status, and cross-manifest validation (shared PR branch) covers all of them. Do not run one command per directory: with --detailed-exitcode the first exits 2 and the second never runs
  • --changed-since needs the ref in the checkout: actions/checkout with fetch-depth: 0
  • --auto-approve on apply (and import --into) in CI; the prompt needs a TTY
  • capture exit codes instead of letting the step fail: ... --detailed-exitcode ... || echo "code=$?" >> "$GITHUB_OUTPUT", then if: steps.plan.outputs.code == '1' -> exit 1. Exit 0 no changes (also when --changed-since selected nothing), 1 error (wins over changes; also bad ref, no manifests), 2 changes
  • --ci is deprecated (exits 1 for changes and errors alike); use --detailed-exitcode, and NO_COLOR=1 for plain output
  • pull request workflow: permissions: pull-requests: write; skip PRs from forks (if: github.event.pull_request.head.repo.full_name == github.repository) since they get no secrets and a read-only token; never suggest pull_request_target for this (it runs the fork's manifests with your token); guard the comment with [ -s plan.md ] (empty when the plan failed early)
  • paths: filters must include directories read through source: / patches: (e.g. templates/**), or a template-only change does not trigger the workflow. Without paths:, --changed-since already makes unrelated runs free. A paths:-filtered workflow cannot be a required check
  • FileSet commit messages can link the trigger: env: GH_INFRA_SOURCE_URL: ${{ github.event.head_commit.url }} on the apply job, used as <% if .Source.URL %>Source: <% .Source.URL %><% end %>

Tokens

  • plan/apply read only what a manifest sets, so grant only the permissions for that (fine-grained PAT or GitHub App token, stored as e.g. GH_INFRA_TOKEN, passed as GH_TOKEN):
  • repository settings (description, topics, features, merge strategy, visibility): plan needs Metadata (+ Contents: read for merge commit messages / auto-merge / pull requests), apply needs Administration: write
  • branch protection, Actions settings, release immutability, vulnerability alerts, automated security fixes: Administration read (plan) / write (apply)
  • rulesets, private vulnerability reporting: plan with Metadata, apply needs Administration: write
  • labels, milestones: Issues; secrets: Secrets; variables: Variables; File/FileSet: Contents (+ Pull requests for via: pull_request)
  • a managed setting the token cannot read fails that repository in plan (cannot read secrets of org/repo (the token needs the Secrets permission)); it is not compared as empty. On GitHub Free private repos, managed rulesets fail with GitHub's "Upgrade to GitHub Pro" message
  • the workflow's GITHUB_TOKEN cannot have Administration and cannot reach other repositories: for its own repo it can plan and apply labels, milestones (issues: write) and File / FileSet (contents: write), not repository settings
  • comments and issues created by the workflow itself can use GH_TOKEN: ${{ github.token }} on that step
  • never use a broad classic PAT

Layouts

gh-infra reads only top-level *.yaml / *.yml in each directory argument.

← v1.0.0All versions