Back to skills
SKILL.md
Github Actions
ASecurityDesign least-privilege GitHub Actions with explicit permissions, OIDC to cloud, cache keys tied to lockfiles, and fork-safe workflows—avoid secret/OIDC footguns agents repeat.
- 2 stars
- 0 votes
- 0 copies
- 0 views
- Added October 22, 2026
Works with
Security analysis
100/100Pro scans all 3 files and shows the line behind each finding
npx -y skills add alivirgo/Major-AI-Skills --skill github-actions --agent claude-codeAre you the author of Github Actions?
Add the live security badge to your README. It updates with every re-scan.
[](https://www.skillsdirectory.com/skills/alivirgo-github-actions)---
name: github-actions
description: "Design least-privilege GitHub Actions with explicit permissions, OIDC to cloud, cache keys tied to lockfiles, and fork-safe workflows—avoid secret/OIDC footguns agents repeat."
category: devops
risk: safe
source: self
source_type: self
date_added: "2026-08-26"
tags: ["github-actions", "ci", "cd", "oidc", "reusable-workflows", "permissions", "supply-chain"]
tools: ["claude", "cursor", "gemini", "codex"]
---
# GitHub Actions CI/CD AI Skill Guide (Claude)
## Overview & Engine Architecture
GitHub Actions runs **workflows** (YAML under `.github/workflows/`) on **events** (`push`, `pull_request`, `workflow_dispatch`, …). Jobs execute on **runners**; steps use `run:` or **actions** from the marketplace. Security is the product: **explicit `permissions`**, **OIDC federation** instead of long-lived cloud keys, **pinned action SHAs** for high assurance, and **fork PR rules** that block secrets and OIDC by design.
```
┌─────────────────────────────────────────────────────────────┐
│ GitHub Actions trust model │
│ │
│ Event → workflow → job(s) → steps │
│ ├── GITHUB_TOKEN (scoped by permissions: block) │
│ ├── Repository / environment secrets │
│ └── OIDC JWT (id-token: write) → cloud IAM role │
│ │
│ Reusable workflow: caller permissions CAP callee │
│ Fork pull_request: read-only token; NO OIDC injection │
└─────────────────────────────────────────────────────────────┘
```
---
## When to use / when not to
**Use when**
- Adding CI (lint/test/build) on PRs and release/deploy on protected branches.
- Wiring AWS/GCP/Azure login via OIDC; caching dependencies; matrix builds.
- Debugging failed checks, cache misses, permission errors, or reusable workflow auth.
**Do not use when**
- `pull_request_target` is suggested to “fix” fork OIDC while checking out **untrusted PR code**—refuse; use maintainer-triggered workflows or skip cloud steps on forks.
- Long-lived cloud access keys in repo secrets when OIDC is available.
- Running unreviewed third-party actions with write permissions.
---
## Operational Capabilities & Agent Directives
1. **Set `permissions:` explicitly** at workflow or job level; listing scopes **replaces** repo defaults—include everything needed (`contents: read`, `pull-requests: write`, etc.).
2. **OIDC jobs require `id-token: write`** on the **caller** when using reusable workflows; callee cannot exceed caller caps.
3. **Fork PRs**: assume **no secrets, no OIDC**; gate cloud deploy steps with `if: github.event.pull_request.head.repo.full_name == github.repository` or manual `workflow_dispatch`.
4. **Pin actions** to full commit SHA for deploy workflows; at minimum pin major tags you trust for inner loops.
5. **Never echo secrets**; use `mask` patterns; rotate if leaked in logs.
6. **Cache keys** must hash lockfiles (`package-lock.json`, `poetry.lock`, `go.sum`).
7. **Separate** PR CI from production deploy workflows; use **environments** with required reviewers for prod.
8. **Supply chain**: audit what marketplace actions execute; prefer composite actions you own.
---
## Production Example: CI + OIDC deploy (same-repo PRs)
PR CI:
```yaml
name: ci
on:
pull_request:
push:
branches: [main]
permissions:
contents: read
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: "20"
cache: npm
- run: npm ci
- run: npm test
- run: npm run build
```
Deploy (protected branch + environment):
```yaml
name: deploy
on:
push:
branches: [main]
permissions:
id-token: write
contents: read
jobs:
deploy:
runs-on: ubuntu-latest
environment: production
steps:
- uses: actions/checkout@v4
- uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: arn:aws:iam::123456789012:role/gha-deploy
aws-region: us-east-1
- run: ./scripts/deploy.sh
```
Reusable workflow caller pattern:
```yaml
jobs:
release:
permissions:
id-token: write
contents: read
uses: org/shared/.github/workflows/deploy.yml@v1
secrets: inherit
```
Cloud trust policy must constrain `sub`/`aud` to repo and environment (see GitHub OIDC docs).
---
## Technical Troubleshooting Matrix
| Failure signature | Likely cause | Fix |
| :--- | :--- | :--- |
| `did not inject ACTIONS_ID_TOKEN` | Fork PR or missing `id-token: write` | Same-repo gate; add permission on caller job |
| `Resource not accessible by integration` | Incomplete `permissions:` after tightening | Add required scopes explicitly |
| Secrets empty on PR | Fork or wrong environment | Expected on forks; use env secrets + approval |
| Cache miss every run | Wrong path/hash in key | Include lockfile hash; verify working directory |
| OIDC AssumeRole denied | Trust policy `sub` mismatch | Align repo, ref, environment claims |
| Reusable workflow auth fail | Caller lacks `id-token: write` | Elevate caller job permissions only |
| `pull_request_target` exploit path | Untrusted code with secrets | Never checkout PR head with secrets; use label-gated maintainer flow |
---
## Best Practices
1. Concurrency groups cancel superseded deploys: `concurrency: group: deploy-${{ github.ref }}`.
2. Upload artifacts between jobs; runner disk is ephemeral.
3. Use `workflow_dispatch` inputs for prod promotions when needed.
4. Dependabot for actions + `@dependabot-config` patterns.
5. Pair image build with `@trivy` and sign artifacts where org requires SLSA.
---
## Limitations
- Self-hosted runners need hardening, label strategy, and org isolation.
- Billing/queue behavior differs by plan; not all features on free tier.
- `pull_request_target` security model is easy to misuse—default away from it.
- Stop and ask if cloud trust policies, environment names, or deploy targets are unknown.
---
## Related Skills
- `@docker` — build/push images in jobs
- `@terraform` — plan/apply with environment gates
- `@kubernetes` / `@argocd` — deploy after CI updates Git tags
- `@trivy` — vulnerability gates
---
## Agent Operational Directive
> **MANDATORY**: Declare least-privilege `permissions` on every workflow. Use OIDC for cloud auth; never recommend long-lived cloud keys in GitHub secrets when OIDC is viable. Do not use `pull_request_target` to run untrusted PR code with secrets or OIDC. For fork PRs, skip or split cloud-authenticated jobs. Pin deploy actions to SHAs when writing high-assurance pipelines.
---
## Source anchors (research)
- [GitHub OIDC reference](https://docs.github.com/en/actions/reference/security/oidc)
- [Reusable workflow id-token caller cap](https://latchkey.dev/learn/github-actions/reusable-workflow-id-token-not-granted-in-ci)
- [Fork PR OIDC injection failure (issue example)](https://github.com/linera-io/linera-protocol/issues/5751)
- [pull_request_target security (Stack Overflow summary)](https://stackoverflow.com/questions/76952023/how-to-make-github-actions-safely-access-secrets-for-prs-created-from-forks)
Files in this skill
- SKILL.md
- gemini.md
- gpt.md
Attribution
Comments
Loading comments…
Newsletter
Get the weekly list of safe new skills, and the ones we pulled.