From 4abf125a4d4d321f2743dcbfd56494d8049ab5a4 Mon Sep 17 00:00:00 2001 From: DJ Date: Sat, 4 Apr 2026 05:46:07 -0700 Subject: [PATCH 01/11] docs: add GitHub repository settings standards Document the standard org and repo configurations including branch protection, rulesets, merge settings, required integrations, labels, and new-repo onboarding checklist. Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 187 +++++++++++++++++++++++++++++++++++ 1 file changed, 187 insertions(+) create mode 100644 standards/github-settings.md diff --git a/standards/github-settings.md b/standards/github-settings.md new file mode 100644 index 0000000..716165d --- /dev/null +++ b/standards/github-settings.md @@ -0,0 +1,187 @@ +# GitHub Repository Settings Standards + +Standard configurations for all repositories in the **petry-projects** organization. +These settings are enforced via the GitHub UI, API, and repository rulesets. + +--- + +## Organization-Level Settings + +| Setting | Value | Notes | +|---------|-------|-------| +| **Default repository permission** | `read` | Members get read access; write access is per-repo | +| **Organization profile** | `petry-projects` | Public org | +| **Dependabot security updates** | Enabled | Org-wide default; repos inherit unless overridden | + +--- + +## Repository Settings — Standard Defaults + +All new repositories MUST be created with these settings. Existing repositories +SHOULD be audited and brought into compliance. + +### General + +| Setting | Standard Value | Rationale | +|---------|---------------|-----------| +| **Default branch** | `main` | All repos use `main` | +| **Visibility** | `public` | Default for org repos; private repos require justification | +| **Has Issues** | `true` | Issue tracking enabled on all repos | +| **Has Projects** | `false` | GitHub Projects disabled by default (use org-level projects if needed) | +| **Has Wiki** | `false` | Wiki disabled; documentation lives in the repo | +| **Has Discussions** | `false` | Disabled by default | + +### Merge Settings + +| Setting | Standard Value | Rationale | +|---------|---------------|-----------| +| **Allow squash merging** | `true` | **Primary merge method** — enforced by `pr-quality` ruleset | +| **Allow merge commits** | `true` | Enabled but not used in practice; ruleset restricts to squash | +| **Allow rebase merging** | `true` | Enabled but not used in practice; ruleset restricts to squash | +| **Allow auto-merge** | `true` | Required for Dependabot auto-merge workflow | +| **Automatically delete head branches** | `true` | Clean up merged branches automatically | +| **Default squash merge commit title** | PR title | Keeps commit history clean | +| **Default squash merge commit message** | PR body | Preserves PR description in commit | + +> **Note:** While merge commits and rebase merging are enabled at the repository +> level, the `pr-quality` ruleset enforces **squash-only** merges. The repo-level +> settings are permissive to avoid conflicts with admin overrides when needed. + +--- + +## Branch Protection — Classic Rules + +All repositories enforce classic branch protection on the `main` branch. + +### Standard Configuration + +| Setting | Value | +|---------|-------| +| **Require pull request before merging** | Yes | +| **Required approving reviews** | 1 | +| **Dismiss stale reviews** | No | +| **Require code owner reviews** | No | +| **Require status checks to pass** | Yes | +| **Require branches to be up to date** | Yes (`strict: true`) | +| **Enforce for admins** | Yes | +| **Allow force pushes** | No | +| **Allow deletions** | No | + +### Required Status Checks by Repository + +Each repository has specific required status checks based on its tech stack and +CI configuration. The table below lists the current required checks: + +| Repository | Required Checks | Stack | +|------------|----------------|-------| +| **broodly** | `Analyze` (CodeQL) | Rust | +| **markets** | `SonarCloud`, `claude` | TypeScript/Go fullstack | +| **google-app-scripts** | `build-and-test` | TypeScript (Apps Script) | +| **TalkTerm** | `Analyze (Python)` (CodeQL) | Python | +| **ContentTwin** | `SonarCloud` | TypeScript | +| **bmad-bgreat-suite** | *(pending — new repo)* | TypeScript | + +When adding a new repository, configure the required status checks to match the +tools and checks available for its tech stack (see [CI Standards](ci-standards.md)). + +--- + +## Repository Rulesets + +### `pr-quality` (All Repositories) + +The `pr-quality` ruleset is applied to all org repos and enforces merge +discipline beyond what classic branch protection provides. + +| Setting | Value | +|---------|-------| +| **Target branches** | Default branch (`main`) | +| **Required approving reviews** | 1 | +| **Required review thread resolution** | **Yes** — all threads must be Resolved before merge | +| **Dismiss stale reviews on push** | No | +| **Require code owner review** | No | +| **Require last push approval** | No | +| **Allowed merge methods** | **Squash only** | + +### `protect-branches` (google-app-scripts) + +The `google-app-scripts` repository has an additional ruleset with stricter +enforcement: + +| Setting | Value | +|---------|-------| +| **Code scanning enforcement** | CodeQL required | +| **Stricter review settings** | Additional review requirements | + +--- + +## GitHub Apps & Integrations + +### Required Integrations + +| App / Integration | Purpose | Scope | +|-------------------|---------|-------| +| **CodeRabbit** | AI-powered code review on PRs | All repos | +| **GitHub Copilot** | AI code review (native) | All repos | +| **SonarCloud** | Code quality, security hotspots, coverage | Repos with SonarCloud checks | +| **CodeQL** | Static analysis (SAST) | Repos with CodeQL workflows | +| **Dependabot** | Security updates for dependencies | All repos (see [Dependabot Policy](dependabot-policy.md)) | + +### GitHub App for Auto-Merge + +A GitHub App is used to provide the approving review required by branch +protection for automated Dependabot merges. Each repository that uses the +Dependabot auto-merge workflow must have these secrets configured: + +| Secret | Purpose | +|--------|---------| +| `APP_ID` | GitHub App ID | +| `APP_PRIVATE_KEY` | GitHub App private key | + +--- + +## Labels — Standard Set + +All repositories SHOULD have these labels available: + +| Label | Color | Purpose | +|-------|-------|---------| +| `security` | `#d93f0b` (red) | Security-related PRs and issues | +| `dependencies` | `#0075ca` (blue) | Dependency update PRs | +| `scorecard` | `#d93f0b` (red) | OpenSSF Scorecard findings (auto-created) | +| `bug` | `#d73a4a` (red) | Bug reports | +| `enhancement` | `#a2eeef` (teal) | Feature requests | +| `documentation` | `#0075ca` (blue) | Documentation changes | + +--- + +## Applying to a New Repository + +When creating a new repository in `petry-projects`: + +1. **Create the repo** with standard settings (public, `main` branch, no wiki/projects) +2. **Enable branch protection** on `main` with the standard configuration above +3. **Create the `pr-quality` ruleset** (or apply the org-level ruleset if available) +4. **Add Dependabot configuration** — copy the appropriate template from + [`standards/dependabot/`](dependabot/) and add to `.github/dependabot.yml` +5. **Add CI workflows** — see [CI Standards](ci-standards.md) for required workflows +6. **Configure secrets** — add `APP_ID` and `APP_PRIVATE_KEY` for Dependabot auto-merge +7. **Create standard labels** — `security`, `dependencies`, plus any project-specific labels +8. **Enable auto-delete head branches** in repo settings +9. **Connect integrations** — ensure CodeRabbit and SonarCloud (if applicable) are enabled + +--- + +## Audit & Compliance + +The org runs a weekly [OpenSSF Scorecard](https://github.com/ossf/scorecard) +audit via the [`org-scorecard.yml`](../.github/workflows/org-scorecard.yml) +workflow. This workflow: + +- Scans all public repos in the org +- Creates/updates GitHub Issues for findings (labeled `scorecard`) +- Auto-closes issues when checks reach a score of 10/10 +- Produces a summary report in the workflow step summary + +Scorecard results should be reviewed weekly and remediated per the +[OpenSSF Scorecard documentation](https://github.com/ossf/scorecard/blob/main/docs/checks.md). From 0ff5b3298e5b9e05a10a996a2cb6e826fbb4f70b Mon Sep 17 00:00:00 2001 From: DJ Date: Sat, 4 Apr 2026 05:52:11 -0700 Subject: [PATCH 02/11] fix: address CodeRabbit review feedback - Improve merge settings rationale to clarify admin override purpose inline - Replace vague protect-branches description with specific ruleset details from the actual GitHub API configuration Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index 716165d..257b03f 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -36,8 +36,8 @@ SHOULD be audited and brought into compliance. | Setting | Standard Value | Rationale | |---------|---------------|-----------| | **Allow squash merging** | `true` | **Primary merge method** — enforced by `pr-quality` ruleset | -| **Allow merge commits** | `true` | Enabled but not used in practice; ruleset restricts to squash | -| **Allow rebase merging** | `true` | Enabled but not used in practice; ruleset restricts to squash | +| **Allow merge commits** | `true` | Enabled to avoid conflicts with admin overrides; `pr-quality` ruleset enforces squash-only | +| **Allow rebase merging** | `true` | Enabled to avoid conflicts with admin overrides; `pr-quality` ruleset enforces squash-only | | **Allow auto-merge** | `true` | Required for Dependabot auto-merge workflow | | **Automatically delete head branches** | `true` | Clean up merged branches automatically | | **Default squash merge commit title** | PR title | Keeps commit history clean | @@ -105,13 +105,18 @@ discipline beyond what classic branch protection provides. ### `protect-branches` (google-app-scripts) -The `google-app-scripts` repository has an additional ruleset with stricter -enforcement: +The `google-app-scripts` repository has an additional ruleset that layers on +top of `pr-quality` with code scanning gates and tighter review policies: | Setting | Value | |---------|-------| -| **Code scanning enforcement** | CodeQL required | -| **Stricter review settings** | Additional review requirements | +| **Required approving reviews** | 0 (relies on `pr-quality` for approval requirement) | +| **Dismiss stale reviews on push** | Yes | +| **Required review thread resolution** | Yes | +| **Allowed merge methods** | Squash only | +| **Code scanning — CodeQL** | Errors threshold: `errors`; Security alerts: `high_or_higher` | +| **Required status checks** | `Analyze (CodeQL) (javascript)`, `CodeQL`, `coverage` | +| **Branch restrictions** | No direct push, no deletion, no non-fast-forward, no branch creation | --- From c970bac53de10c6aefd6c8262a866fc9b6fb14b5 Mon Sep 17 00:00:00 2001 From: DJ Date: Sat, 4 Apr 2026 06:04:21 -0700 Subject: [PATCH 03/11] fix: correct settings values from API audit data - Fix org default permission to 'write' (not 'read') - Fix has_projects to 'true' (currently enabled on all repos) - Fix has_wiki to 'true' (enabled on most repos) - Fix squash commit message to COMMIT_MESSAGES (not PR body) - Fix broodly stack label (TypeScript + Go, not Rust) - Add installed GitHub Apps with dates from API audit - Add compliance status table showing per-repo deviations Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 63 ++++++++++++++++++++++++------------ 1 file changed, 43 insertions(+), 20 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index 257b03f..72f9041 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -9,9 +9,11 @@ These settings are enforced via the GitHub UI, API, and repository rulesets. | Setting | Value | Notes | |---------|-------|-------| -| **Default repository permission** | `read` | Members get read access; write access is per-repo | -| **Organization profile** | `petry-projects` | Public org | -| **Dependabot security updates** | Enabled | Org-wide default; repos inherit unless overridden | +| **Default repository permission** | `write` | Members get write access by default | +| **Organization profile** | `petry-projects` | Public org (free plan) | +| **Default branch name** | `main` | Org-wide default for new repos | +| **Members can create repos** | Yes (public + private) | | +| **Two-factor requirement** | Disabled | Consider enabling for security | --- @@ -27,8 +29,8 @@ SHOULD be audited and brought into compliance. | **Default branch** | `main` | All repos use `main` | | **Visibility** | `public` | Default for org repos; private repos require justification | | **Has Issues** | `true` | Issue tracking enabled on all repos | -| **Has Projects** | `false` | GitHub Projects disabled by default (use org-level projects if needed) | -| **Has Wiki** | `false` | Wiki disabled; documentation lives in the repo | +| **Has Projects** | `true` | Currently enabled on all repos | +| **Has Wiki** | `true` | Currently enabled on most repos (consider disabling — docs live in repo) | | **Has Discussions** | `false` | Disabled by default | ### Merge Settings @@ -40,8 +42,8 @@ SHOULD be audited and brought into compliance. | **Allow rebase merging** | `true` | Enabled to avoid conflicts with admin overrides; `pr-quality` ruleset enforces squash-only | | **Allow auto-merge** | `true` | Required for Dependabot auto-merge workflow | | **Automatically delete head branches** | `true` | Clean up merged branches automatically | -| **Default squash merge commit title** | PR title | Keeps commit history clean | -| **Default squash merge commit message** | PR body | Preserves PR description in commit | +| **Default squash merge commit title** | PR title (`COMMIT_OR_PR_TITLE`) | Keeps commit history clean | +| **Default squash merge commit message** | Commit messages (`COMMIT_MESSAGES`) | Preserves individual commit messages | > **Note:** While merge commits and rebase merging are enabled at the repository > level, the `pr-quality` ruleset enforces **squash-only** merges. The repo-level @@ -74,7 +76,7 @@ CI configuration. The table below lists the current required checks: | Repository | Required Checks | Stack | |------------|----------------|-------| -| **broodly** | `Analyze` (CodeQL) | Rust | +| **broodly** | `Analyze` (CodeQL) | TypeScript + Go fullstack | | **markets** | `SonarCloud`, `claude` | TypeScript/Go fullstack | | **google-app-scripts** | `build-and-test` | TypeScript (Apps Script) | | **TalkTerm** | `Analyze (Python)` (CodeQL) | Python | @@ -122,25 +124,31 @@ top of `pr-quality` with code scanning gates and tighter review policies: ## GitHub Apps & Integrations -### Required Integrations +### Installed GitHub Apps (org-wide, all repos) -| App / Integration | Purpose | Scope | -|-------------------|---------|-------| -| **CodeRabbit** | AI-powered code review on PRs | All repos | -| **GitHub Copilot** | AI code review (native) | All repos | -| **SonarCloud** | Code quality, security hotspots, coverage | Repos with SonarCloud checks | -| **CodeQL** | Static analysis (SAST) | Repos with CodeQL workflows | +| App | Purpose | Installed | +|-----|---------|-----------| +| **Claude** | AI code review and PR assistance via Claude Code Action | 2026-03-20 | +| **dependabot-automerge-petry** | Provides approving review for Dependabot auto-merge (bypasses branch protection) | 2026-03-23 | +| **SonarQube Cloud (SonarCloud)** | Code quality, security hotspots, coverage tracking | 2026-03-25 | +| **CodeRabbit AI** | AI-powered code review on PRs | 2026-03-25 | + +### Other Integrations + +| Integration | Purpose | Scope | +|-------------|---------|-------| +| **GitHub Copilot** | AI code review (native GitHub feature) | All repos | +| **CodeQL** | Static analysis (SAST) via GitHub Actions | Repos with CodeQL workflows | | **Dependabot** | Security updates for dependencies | All repos (see [Dependabot Policy](dependabot-policy.md)) | -### GitHub App for Auto-Merge +### GitHub App Secrets for Auto-Merge -A GitHub App is used to provide the approving review required by branch -protection for automated Dependabot merges. Each repository that uses the -Dependabot auto-merge workflow must have these secrets configured: +The `dependabot-automerge-petry` app provides the approving review required by +branch protection for automated Dependabot merges. Each repository must have: | Secret | Purpose | |--------|---------| -| `APP_ID` | GitHub App ID | +| `APP_ID` | GitHub App ID (app_id: 3167543) | | `APP_PRIVATE_KEY` | GitHub App private key | --- @@ -177,6 +185,21 @@ When creating a new repository in `petry-projects`: --- +## Current Compliance Status + +Settings deviations from the standard documented above: + +| Repository | Deviations | +|------------|-----------| +| **bmad-bgreat-suite** | No branch protection, no rulesets, `delete_branch_on_merge: false`, `allow_auto_merge: false` | +| **ContentTwin** | `has_wiki: false`, `allow_auto_merge: false` | +| **google-app-scripts** | `allow_merge_commit: false`, `allow_rebase_merge: false` (stricter than standard) | +| **broodly** | Compliant | +| **markets** | Compliant | +| **TalkTerm** | Compliant | + +--- + ## Audit & Compliance The org runs a weekly [OpenSSF Scorecard](https://github.com/ossf/scorecard) From 01bdc1f29e665a098966708fa9262c5abaf94b09 Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 08:19:38 -0700 Subject: [PATCH 04/11] =?UTF-8?q?refactor:=20apply=20review=20feedback=20?= =?UTF-8?q?=E2=80=94=20rulesets,=20settings,=20and=20secrets?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Change wiki to disabled, discussions to enabled - Change squash commit title to PR_TITLE - Replace classic branch protection with rulesets-first approach - Strengthen pr-quality ruleset: dismiss stale reviews, require last push approval, require code owner review - Abstract required checks into conditional code-quality ruleset (removes repo-specific names, uses condition-based check mapping) - Fix GitHub App secrets to reflect org-level inheritance - Update new-repo checklist and compliance status accordingly - Add migration note for classic → ruleset transition Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 135 ++++++++++++++++------------------- 1 file changed, 63 insertions(+), 72 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index 72f9041..11d7d4b 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -30,8 +30,8 @@ SHOULD be audited and brought into compliance. | **Visibility** | `public` | Default for org repos; private repos require justification | | **Has Issues** | `true` | Issue tracking enabled on all repos | | **Has Projects** | `true` | Currently enabled on all repos | -| **Has Wiki** | `true` | Currently enabled on most repos (consider disabling — docs live in repo) | -| **Has Discussions** | `false` | Disabled by default | +| **Has Wiki** | `false` | Disabled — documentation lives in the repo | +| **Has Discussions** | `true` | Enabled for community engagement | ### Merge Settings @@ -42,7 +42,7 @@ SHOULD be audited and brought into compliance. | **Allow rebase merging** | `true` | Enabled to avoid conflicts with admin overrides; `pr-quality` ruleset enforces squash-only | | **Allow auto-merge** | `true` | Required for Dependabot auto-merge workflow | | **Automatically delete head branches** | `true` | Clean up merged branches automatically | -| **Default squash merge commit title** | PR title (`COMMIT_OR_PR_TITLE`) | Keeps commit history clean | +| **Default squash merge commit title** | `PR_TITLE` | Clean, descriptive commit history | | **Default squash merge commit message** | Commit messages (`COMMIT_MESSAGES`) | Preserves individual commit messages | > **Note:** While merge commits and rebase merging are enabled at the repository @@ -51,74 +51,54 @@ SHOULD be audited and brought into compliance. --- -## Branch Protection — Classic Rules +## Repository Rulesets -All repositories enforce classic branch protection on the `main` branch. +Rulesets are the primary enforcement mechanism for branch policies. All +repositories MUST use rulesets on the default branch. Classic branch protection +rules are deprecated — migrate existing classic rules to rulesets. -### Standard Configuration +### `pr-quality` — Standard Ruleset (All Repositories) | Setting | Value | |---------|-------| -| **Require pull request before merging** | Yes | +| **Target branches** | Default branch (`main`) | +| **Enforcement** | Active | | **Required approving reviews** | 1 | -| **Dismiss stale reviews** | No | -| **Require code owner reviews** | No | -| **Require status checks to pass** | Yes | -| **Require branches to be up to date** | Yes (`strict: true`) | -| **Enforce for admins** | Yes | +| **Dismiss stale reviews on push** | **Yes** — prevents merging unreviewed code after approval | +| **Required review thread resolution** | **Yes** — all threads must be Resolved before merge | +| **Require code owner review** | **Yes** — requires approval from a CODEOWNERS-defined owner | +| **Require last push approval** | **Yes** — the person who pushed last cannot be the sole approver | +| **Allowed merge methods** | **Squash only** | | **Allow force pushes** | No | | **Allow deletions** | No | -### Required Status Checks by Repository +> **CODEOWNERS:** Repos SHOULD add a `CODEOWNERS` file defining ownership. +> Without one, the "Require code owner review" setting has no effect. Add +> CODEOWNERS incrementally as team structure and domain ownership solidifies. -Each repository has specific required status checks based on its tech stack and -CI configuration. The table below lists the current required checks: +### `code-quality` — Conditional Checks Ruleset -| Repository | Required Checks | Stack | -|------------|----------------|-------| -| **broodly** | `Analyze` (CodeQL) | TypeScript + Go fullstack | -| **markets** | `SonarCloud`, `claude` | TypeScript/Go fullstack | -| **google-app-scripts** | `build-and-test` | TypeScript (Apps Script) | -| **TalkTerm** | `Analyze (Python)` (CodeQL) | Python | -| **ContentTwin** | `SonarCloud` | TypeScript | -| **bmad-bgreat-suite** | *(pending — new repo)* | TypeScript | +Required status checks are configured per-repo based on which tools are +present. Add checks to this ruleset when the corresponding configuration exists +in the repository: -When adding a new repository, configure the required status checks to match the -tools and checks available for its tech stack (see [CI Standards](ci-standards.md)). +| Condition | Required Check(s) | +|-----------|--------------------| +| Repo has a `sonarcloud.yml` workflow or `sonar-project.properties` | `SonarCloud` | +| Repo has a `codeql.yml` workflow | `Analyze` (or `Analyze ()` for multi-language) | +| Repo has a `claude.yml` workflow | `claude` | +| Repo has a `ci.yml` workflow | CI job name (e.g., `build-and-test`, `TypeScript`, `Go`) | +| Repo has a `coverage.yml` or coverage step | `coverage` | ---- - -## Repository Rulesets - -### `pr-quality` (All Repositories) - -The `pr-quality` ruleset is applied to all org repos and enforces merge -discipline beyond what classic branch protection provides. +Additional settings: | Setting | Value | |---------|-------| -| **Target branches** | Default branch (`main`) | -| **Required approving reviews** | 1 | -| **Required review thread resolution** | **Yes** — all threads must be Resolved before merge | -| **Dismiss stale reviews on push** | No | -| **Require code owner review** | No | -| **Require last push approval** | No | -| **Allowed merge methods** | **Squash only** | - -### `protect-branches` (google-app-scripts) - -The `google-app-scripts` repository has an additional ruleset that layers on -top of `pr-quality` with code scanning gates and tighter review policies: +| **Require branches to be up to date** | Yes (`strict: true`) | +| **Enforce for admins** | Yes | -| Setting | Value | -|---------|-------| -| **Required approving reviews** | 0 (relies on `pr-quality` for approval requirement) | -| **Dismiss stale reviews on push** | Yes | -| **Required review thread resolution** | Yes | -| **Allowed merge methods** | Squash only | -| **Code scanning — CodeQL** | Errors threshold: `errors`; Security alerts: `high_or_higher` | -| **Required status checks** | `Analyze (CodeQL) (javascript)`, `CodeQL`, `coverage` | -| **Branch restrictions** | No direct push, no deletion, no non-fast-forward, no branch creation | +When adding a new repository, determine which CI tools apply to its stack +(see [CI Standards](ci-standards.md)) and add the corresponding checks. --- @@ -144,12 +124,15 @@ top of `pr-quality` with code scanning gates and tighter review policies: ### GitHub App Secrets for Auto-Merge The `dependabot-automerge-petry` app provides the approving review required by -branch protection for automated Dependabot merges. Each repository must have: +rulesets for automated Dependabot merges. These secrets are configured at the +**organization level** and inherited by all repos: -| Secret | Purpose | -|--------|---------| -| `APP_ID` | GitHub App ID (app_id: 3167543) | -| `APP_PRIVATE_KEY` | GitHub App private key | +| Secret | Level | Purpose | +|--------|-------|---------| +| `APP_ID` | Organization | GitHub App ID (app_id: 3167543) | +| `APP_PRIVATE_KEY` | Organization | GitHub App private key | + +New repositories automatically inherit these secrets — no per-repo configuration needed. --- @@ -172,17 +155,21 @@ All repositories SHOULD have these labels available: When creating a new repository in `petry-projects`: -1. **Create the repo** with standard settings (public, `main` branch, no wiki/projects) -2. **Enable branch protection** on `main` with the standard configuration above -3. **Create the `pr-quality` ruleset** (or apply the org-level ruleset if available) -4. **Add Dependabot configuration** — copy the appropriate template from +1. **Create the repo** with standard settings (public, `main` branch, wiki disabled, discussions enabled) +2. **Create the `pr-quality` ruleset** matching the standard configuration above +3. **Create the `code-quality` ruleset** with required checks for the repo's stack +4. **Add a `CODEOWNERS` file** defining ownership for the repo's key paths +5. **Add Dependabot configuration** — copy the appropriate template from [`standards/dependabot/`](dependabot/) and add to `.github/dependabot.yml` -5. **Add CI workflows** — see [CI Standards](ci-standards.md) for required workflows -6. **Configure secrets** — add `APP_ID` and `APP_PRIVATE_KEY` for Dependabot auto-merge +6. **Add CI workflows** — see [CI Standards](ci-standards.md) for required workflows 7. **Create standard labels** — `security`, `dependencies`, plus any project-specific labels -8. **Enable auto-delete head branches** in repo settings +8. **Enable auto-delete head branches** and **auto-merge** in repo settings 9. **Connect integrations** — ensure CodeRabbit and SonarCloud (if applicable) are enabled +> **Note:** Org-level secrets (`APP_ID`, `APP_PRIVATE_KEY`, `CLAUDE_CODE_OAUTH_TOKEN`) +> are inherited automatically. Repo-specific secrets (e.g., `SONAR_TOKEN`, GCP +> credentials) must be configured per-repo. + --- ## Current Compliance Status @@ -191,12 +178,16 @@ Settings deviations from the standard documented above: | Repository | Deviations | |------------|-----------| -| **bmad-bgreat-suite** | No branch protection, no rulesets, `delete_branch_on_merge: false`, `allow_auto_merge: false` | -| **ContentTwin** | `has_wiki: false`, `allow_auto_merge: false` | -| **google-app-scripts** | `allow_merge_commit: false`, `allow_rebase_merge: false` (stricter than standard) | -| **broodly** | Compliant | -| **markets** | Compliant | -| **TalkTerm** | Compliant | +| **bmad-bgreat-suite** | No rulesets, `delete_branch_on_merge: false`, `allow_auto_merge: false`, `has_wiki: true`, `has_discussions: false` | +| **ContentTwin** | `allow_auto_merge: false`, `has_discussions: false` | +| **google-app-scripts** | `allow_merge_commit: false`, `allow_rebase_merge: false` (stricter than standard), `has_discussions: false` | +| **broodly** | `has_wiki: true`, `has_discussions: false` | +| **markets** | `has_wiki: true`, `has_discussions: false` | +| **TalkTerm** | `has_wiki: true`, `has_discussions: false` | + +> **Migration note:** All repos currently use classic branch protection. These +> should be migrated to rulesets per the standard above. Classic rules should +> be removed after rulesets are verified. --- From d2374eddbcfaf12de1ea6ba1e4f74105c86a3106 Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 08:23:54 -0700 Subject: [PATCH 05/11] fix: require 2FA and align label onboarding checklist - Set two-factor requirement to Required (was Disabled) - Reference full standard label set in onboarding checklist Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index 11d7d4b..adb1e49 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -13,7 +13,7 @@ These settings are enforced via the GitHub UI, API, and repository rulesets. | **Organization profile** | `petry-projects` | Public org (free plan) | | **Default branch name** | `main` | Org-wide default for new repos | | **Members can create repos** | Yes (public + private) | | -| **Two-factor requirement** | Disabled | Consider enabling for security | +| **Two-factor requirement** | **Required** | All org members must have 2FA enabled | --- @@ -162,7 +162,7 @@ When creating a new repository in `petry-projects`: 5. **Add Dependabot configuration** — copy the appropriate template from [`standards/dependabot/`](dependabot/) and add to `.github/dependabot.yml` 6. **Add CI workflows** — see [CI Standards](ci-standards.md) for required workflows -7. **Create standard labels** — `security`, `dependencies`, plus any project-specific labels +7. **Create standard labels** — all labels from the [Standard Set](#labels--standard-set) above, plus any project-specific labels 8. **Enable auto-delete head branches** and **auto-merge** in repo settings 9. **Connect integrations** — ensure CodeRabbit and SonarCloud (if applicable) are enabled From 7c619ec7ad87d3b39c733fec290b56e91dd5d223 Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 08:27:35 -0700 Subject: [PATCH 06/11] fix: tighten org permission to read, make labels MUST - Change default repo permission to 'read' (least privilege) - Change labels from SHOULD to MUST for consistency with onboarding checklist Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index adb1e49..dde1747 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -9,7 +9,7 @@ These settings are enforced via the GitHub UI, API, and repository rulesets. | Setting | Value | Notes | |---------|-------|-------| -| **Default repository permission** | `write` | Members get write access by default | +| **Default repository permission** | `read` | Least privilege; grant write/admin via teams | | **Organization profile** | `petry-projects` | Public org (free plan) | | **Default branch name** | `main` | Org-wide default for new repos | | **Members can create repos** | Yes (public + private) | | @@ -138,7 +138,7 @@ New repositories automatically inherit these secrets — no per-repo configurati ## Labels — Standard Set -All repositories SHOULD have these labels available: +All repositories MUST have these labels configured: | Label | Color | Purpose | |-------|-------|---------| From d3907cbd04b4fba85cb311490b49da7e0cde643f Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 09:29:36 -0700 Subject: [PATCH 07/11] refactor: make all quality checks required on all repos MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit All five check categories (SonarCloud, CodeQL, Claude Code, CI, Coverage) are now universally required. Ecosystem-specific configuration varies by what languages/tools the repo contains — if an ecosystem is present, it must be configured in the relevant checks. Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/ci-standards.md | 454 +++++++++++++++++++++++++++++++++++ standards/github-settings.md | 47 ++-- 2 files changed, 487 insertions(+), 14 deletions(-) create mode 100644 standards/ci-standards.md diff --git a/standards/ci-standards.md b/standards/ci-standards.md new file mode 100644 index 0000000..f23d532 --- /dev/null +++ b/standards/ci-standards.md @@ -0,0 +1,454 @@ +# CI/CD Standards + +Standard CI/CD configurations for all repositories in the **petry-projects** organization. +This document defines the required workflows, quality gates, and patterns that every +repository must implement. + +--- + +## Required Workflows + +Every repository MUST have these workflows. Reusable templates for Dependabot +workflows are in [`standards/workflows/`](workflows/). The CI, CodeQL, +SonarCloud, and Claude Code workflows are documented as patterns below — copy +and adapt the examples to each repo's tech stack. + +### 1. CI Pipeline (`ci.yml`) + +The primary build-and-test workflow. Structure varies by tech stack but must include: + +| Stage | Purpose | Required | +|-------|---------|----------| +| **Lint** | Static analysis / style enforcement | Yes | +| **Format check** | Formatting verification | Yes | +| **Type check** | Type safety (where applicable) | Yes | +| **Unit tests** | Fast, deterministic tests | Yes | +| **Coverage** | Code coverage reporting | Yes | +| **Integration tests** | Backend/API integration | If applicable | +| **E2E tests** | End-to-end functional tests | If applicable | +| **Build / Docker build** | Verify the artifact builds | If applicable | + +**Standard triggers:** + +```yaml +on: + push: + branches: [main] + pull_request: + branches: [main] +``` + +**Standard configuration patterns:** + +```yaml +permissions: {} # Reset top-level; set per-job (see Permissions Policy below) + +concurrency: + group: ci-${{ github.ref }} + cancel-in-progress: true +``` + +### 2. CodeQL Analysis (`codeql.yml`) + +Static Application Security Testing (SAST) via GitHub's CodeQL. + +**Standard configuration:** + +```yaml +on: + push: + branches: [main] + pull_request: + branches: [main] + schedule: + - cron: '25 14 * * 3' # Weekly scan (Wednesday) +``` + +**Language matrix by repo:** + +| Repository | CodeQL Language(s) | +|------------|-------------------| +| **broodly** | `actions` | +| **google-app-scripts** | `javascript-typescript` | +| **TalkTerm** | `python` (pending: `javascript-typescript`) | +| **markets** | `javascript-typescript` | +| **ContentTwin** | `javascript-typescript` (pending) | + +### 3. SonarCloud Analysis (`sonarcloud.yml`) + +Code quality, maintainability, security hotspots, and coverage tracking. + +**Standard configuration:** + +```yaml +name: SonarCloud Analysis + +permissions: {} + +on: + push: + branches: [main] + pull_request: + branches: [main] + +jobs: + sonarcloud: + name: SonarCloud + runs-on: ubuntu-latest + permissions: + contents: read + pull-requests: read + env: + SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} + steps: + - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + with: + fetch-depth: 0 + - name: SonarCloud Scan + if: ${{ env.SONAR_TOKEN != '' }} + uses: SonarSource/sonarqube-scan-action@a31c9398be7ace6bbfaf30c0bd5d415f843d45e9 # v7.0.0 +``` + +**Required secrets:** `SONAR_TOKEN` + +Each repo needs a `sonar-project.properties` file at root with project key and org. + +### 4. Claude Code (`claude.yml`) + +AI-assisted code review via Claude Code Action on PRs. Also responds to +`@claude` mentions in PR comments. + +**Standard configuration:** + +```yaml +name: Claude Code + +on: + pull_request: + branches: [main] + types: [opened, reopened, synchronize] + issue_comment: + types: [created] + pull_request_review_comment: + types: [created] + +permissions: {} + +jobs: + claude: + if: >- + (github.event_name == 'pull_request' && + github.event.pull_request.head.repo.full_name == github.repository) || + (github.event_name == 'issue_comment' && github.event.issue.pull_request && + contains(github.event.comment.body, '@claude') && + contains(fromJson('["OWNER","MEMBER","COLLABORATOR"]'), github.event.comment.author_association)) || + (github.event_name == 'pull_request_review_comment' && + contains(github.event.comment.body, '@claude') && + contains(fromJson('["OWNER","MEMBER","COLLABORATOR"]'), github.event.comment.author_association)) + runs-on: ubuntu-latest + timeout-minutes: 60 + permissions: + contents: read + id-token: write + pull-requests: write + issues: write + steps: + - name: Run Claude Code + if: github.event_name != 'pull_request' || github.event.pull_request.user.login != 'dependabot[bot]' + uses: anthropics/claude-code-action@bee87b3258c251f9279e5371b0cc3660f37f3f77 # v1 + with: + claude_code_oauth_token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }} +``` + +**Required secrets:** `CLAUDE_CODE_OAUTH_TOKEN` + +**Dependabot behavior:** The Claude Code step is skipped for Dependabot PRs (the +`if` condition on the step). The job still runs and reports SUCCESS to satisfy +required status checks. See [AGENTS.md](../AGENTS.md#claude-code-workflow-on-dependabot-prs). + +### 5. Dependabot Auto-Merge (`dependabot-automerge.yml`) + +Automatically approves and squash-merges eligible Dependabot PRs. +See [`workflows/dependabot-automerge.yml`](workflows/dependabot-automerge.yml) +and the [Dependabot Policy](dependabot-policy.md) for full details. + +### 6. Dependency Audit (`dependency-audit.yml`) + +Vulnerability scanning for all package ecosystems. +See [`workflows/dependency-audit.yml`](workflows/dependency-audit.yml) +and the [Dependabot Policy](dependabot-policy.md). + +--- + +## Workflow Patterns by Tech Stack + +### TypeScript / Node.js (npm) + +```yaml +steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version: '20' # or 'lts/*' + cache: npm + - run: npm ci + - run: npm run check # lint + format + - run: npm run typecheck # tsc --noEmit + - run: npm test # unit tests + coverage +``` + +**Repos using this pattern:** google-app-scripts, ContentTwin + +### TypeScript / Node.js (pnpm) + +```yaml +steps: + - uses: actions/checkout@v4 + - uses: pnpm/action-setup@v4 + - uses: actions/setup-node@v4 + with: + node-version: 20 + cache: pnpm + - run: pnpm install --frozen-lockfile + - run: pnpm run lint + - run: pnpm run typecheck + - run: pnpm run test +``` + +**Repos using this pattern:** broodly (TypeScript layer) + +### Go + +```yaml +steps: + - uses: actions/checkout@v4 + - uses: actions/setup-go@v5 + with: + go-version: 'stable' # Or pin to specific version (e.g., '1.24') matching go.mod + cache-dependency-path: apps/api/go.sum + - run: go vet ./... + - uses: golangci/golangci-lint-action@v6 + - run: go test ./... -race -coverprofile=coverage.out +``` + +**Repos using this pattern:** broodly (Go API) + +### TypeScript + Electron (npm) + +```yaml +strategy: + matrix: + os: [ubuntu-latest, macos-latest, windows-latest] +steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version: 24 + cache: npm + - run: npm ci + - run: npm run typecheck + - run: npm run lint + - run: npm run format:check + - run: npm test + - run: npm run test:coverage +``` + +**Additional jobs for Electron:** +- Mutation testing (`npm run test:mutate`) — `continue-on-error: true` +- E2E tests via Playwright (`npx playwright test`) on macOS — `continue-on-error: true` + +**Repos using this pattern:** TalkTerm + +### Python + +```yaml +steps: + - uses: actions/checkout@v4 + - uses: actions/setup-python@v5 + with: + python-version: '3.x' + # Project-specific: pip install, pytest, etc. +``` + +**Repos using this pattern:** TalkTerm (CodeQL only currently) + +--- + +## Action Pinning Policy + +All GitHub Actions MUST be pinned to a specific commit SHA, not a tag or branch. + +```yaml +# CORRECT — pinned to SHA +- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + +# WRONG — mutable tag +- uses: actions/checkout@v4 +``` + +**Rationale:** SHA pinning prevents supply-chain attacks where a tag is +force-pushed to a malicious commit. The comment after the SHA documents the +version for human readability. + +Dependabot keeps pinned SHAs up to date via the `github-actions` ecosystem +entry in `dependabot.yml`. + +> **Note on examples in this document:** The "Workflow Patterns by Tech Stack" +> section uses tag references (e.g., `@v4`) for readability since those are +> illustrative patterns, not copy-paste templates. The "Required Workflows" +> section above uses SHA-pinned references where possible. When copying any +> example to a repository, always look up the current SHA for each action and +> pin to it with a version comment. + +--- + +## Permissions Policy + +All workflows MUST follow the principle of least privilege: + +```yaml +# Multi-job workflows: reset at top, set per-job +permissions: {} + +jobs: + my-job: + permissions: + contents: read # Only what this job needs +``` + +For single-job workflows, top-level least-privilege permissions are acceptable +(e.g., `permissions: contents: read`) since there is only one job to scope. + +**Common permission sets:** + +| Workflow | Permissions | +|----------|------------| +| CI (build/test) | `contents: read` | +| SonarCloud | `contents: read`, `pull-requests: read` | +| Claude Code | `contents: read`, `id-token: write`, `pull-requests: write`, `issues: write` | +| CodeQL | `actions: read`, `security-events: write`, `contents: read` | +| Dependabot auto-merge | `contents: read`, `pull-requests: read` (+ app token for merge) | + +--- + +## Secrets Required by Repository + +| Secret | Purpose | Repos | +|--------|---------|-------| +| `CLAUDE_CODE_OAUTH_TOKEN` | Claude Code Action authentication | All repos with `claude.yml` | +| `SONAR_TOKEN` | SonarCloud analysis | broodly, markets, ContentTwin, google-app-scripts | +| `APP_ID` | GitHub App for Dependabot auto-merge | All repos with `dependabot-automerge.yml` | +| `APP_PRIVATE_KEY` | GitHub App private key | All repos with `dependabot-automerge.yml` | +| `GCP_PROJECT_ID` | GCP project for container registry | broodly | +| `GCP_WORKLOAD_IDENTITY_PROVIDER` | GCP Workload Identity Federation | broodly | +| `GCP_SERVICE_ACCOUNT` | GCP service account email | broodly | + +--- + +## CI Job Naming Convention + +CI job names become the GitHub status check names that branch protection +references. Use consistent, descriptive names: + +| Pattern | Example | Notes | +|---------|---------|-------| +| Language / tool name | `TypeScript`, `Go`, `SonarCloud` | For multi-language repos | +| `build-and-test` | `build-and-test` | For single-language repos | +| `Analyze` or `Analyze ()` | `Analyze`, `Analyze (Python)` | CodeQL jobs | +| `claude` | `claude` | Claude Code Action | + +These names are referenced in branch protection required status checks. +Changing a job name requires updating the branch protection configuration. + +--- + +## Org-Level Workflows + +The [`.github` repository](https://github.com/petry-projects/.github) contains +org-level workflows that run across all repositories: + +### OpenSSF Scorecard (`org-scorecard.yml`) + +- **Schedule:** Weekly (Monday 9:00 UTC) +- **Purpose:** Security posture scoring for all public repos +- **Behavior:** Creates/updates GitHub Issues with findings, auto-closes resolved findings +- **Skip list:** CII-Best-Practices, Contributors, Fuzzing, Maintained, Packaging, Signed-Releases + +--- + +## CI Auto-Fix Pattern + +Some repositories implement automatic formatting fixes on PRs: + +```yaml +autofix: + needs: build-and-test + if: > + github.event_name == 'pull_request' && + github.event.pull_request.head.repo.full_name == github.repository + runs-on: ubuntu-latest + permissions: + contents: write + steps: + - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + with: + ref: ${{ github.event.pull_request.head.ref }} + - run: npm run format && npm run lint -- --fix + - name: Commit fixes + run: | + if ! git diff --quiet; then + git config user.name "github-actions[bot]" + git config user.email "github-actions[bot]@users.noreply.github.com" + git add -A + git commit -m "chore(ci): apply prettier/eslint auto-fixes" + git push + fi +``` + +**Repos using this pattern:** google-app-scripts + +> **Note:** Auto-fix only runs on same-repo PRs (not forks) since it needs +> write access to the PR branch. + +--- + +## Applying CI to a New Repository + +1. **Determine tech stack** and select the matching workflow patterns above +2. **Create `ci.yml`** with lint, format, typecheck, and test stages +3. **Add `codeql.yml`** with the appropriate language(s) +4. **Add `sonarcloud.yml`** and configure `sonar-project.properties` +5. **Add `claude.yml`** for AI code review +6. **Add `dependabot.yml`** from the appropriate template in [`standards/dependabot/`](dependabot/) +7. **Add `dependabot-automerge.yml`** from [`standards/workflows/`](workflows/) +8. **Add `dependency-audit.yml`** from [`standards/workflows/`](workflows/) +9. **Configure secrets** in the repository settings +10. **Set required status checks** in branch protection (see [GitHub Settings](github-settings.md)) +11. **Pin all action references** to commit SHAs + +--- + +## Current Repository CI Status + +| Repository | CI | CodeQL | SonarCloud | Claude | Dep Auto-merge | Dep Audit | Dependabot Config | +|------------|:--:|:------:|:----------:|:------:|:--------------:|:---------:|:-----------------:| +| **broodly** | Yes | Yes | Yes | Yes | Yes | Yes | Yes | +| **markets** | — | Yes | Yes | Yes | Yes | Yes | Partial (missing npm ecosystem) | +| **google-app-scripts** | Yes | Yes | Yes | Yes | Yes (older pattern) | — | Non-standard (npm limit:10) | +| **TalkTerm** | Yes | — | — | — | — | — | — | +| **ContentTwin** | — | — | Yes | — | — | — | — | +| **bmad-bgreat-suite** | — | — | — | — | — | — | — | + +### Gaps to Address + +- **TalkTerm:** Missing SonarCloud, Claude Code, Dependabot config, auto-merge, dependency audit, CodeQL +- **ContentTwin:** Missing CI pipeline, CodeQL, Claude Code, Dependabot config, auto-merge, dependency audit +- **bmad-bgreat-suite:** Missing all CI workflows (new repo — no branch protection or rulesets either) +- **google-app-scripts:** Missing dependency audit workflow; Dependabot config uses `limit:10` for npm (should be `0` per policy); auto-merge workflow uses older pattern (`--admin` bypass instead of `--auto`) +- **markets:** Missing dedicated CI pipeline; Dependabot config only covers `github-actions` — missing `npm` ecosystem entry + +### Version Inconsistencies + +- **SonarCloud action:** broodly/markets use v7.0.0; ContentTwin/google-app-scripts use v6 +- **CodeQL action:** broodly uses v4; markets uses v3 +- **Claude Code Action:** Different SHA pins across repos (should be aligned) diff --git a/standards/github-settings.md b/standards/github-settings.md index dde1747..e9349df 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -76,29 +76,48 @@ rules are deprecated — migrate existing classic rules to rulesets. > Without one, the "Require code owner review" setting has no effect. Add > CODEOWNERS incrementally as team structure and domain ownership solidifies. -### `code-quality` — Conditional Checks Ruleset +### `code-quality` — Required Checks Ruleset (All Repositories) -Required status checks are configured per-repo based on which tools are -present. Add checks to this ruleset when the corresponding configuration exists -in the repository: +Every repository MUST have all five quality checks configured and required. +The specific check names and ecosystem configurations vary by repo, but the +categories are universal. -| Condition | Required Check(s) | -|-----------|--------------------| -| Repo has a `sonarcloud.yml` workflow or `sonar-project.properties` | `SonarCloud` | -| Repo has a `codeql.yml` workflow | `Analyze` (or `Analyze ()` for multi-language) | -| Repo has a `claude.yml` workflow | `claude` | -| Repo has a `ci.yml` workflow | CI job name (e.g., `build-and-test`, `TypeScript`, `Go`) | -| Repo has a `coverage.yml` or coverage step | `coverage` | +#### Required Check Categories -Additional settings: +| Check | Required | Check Name(s) | Notes | +|-------|----------|---------------|-------| +| **SonarCloud** | All repos | `SonarCloud` | Code quality, maintainability, security hotspots | +| **CodeQL** | All repos | `Analyze` or `Analyze ()` | SAST — language(s) match the repo's ecosystems | +| **Claude Code** | All repos | `claude` | AI code review on every PR | +| **CI Pipeline** | All repos | Repo-specific (e.g., `build-and-test`, `TypeScript`, `Go`) | Lint, format, typecheck, test | +| **Coverage** | All repos | `coverage` or embedded in CI job | Must meet repo-defined thresholds | + +#### Ecosystem-Specific Configuration + +The ecosystems scanned by each check depend on which languages/tools the repo +contains. If a repo contains an ecosystem, that ecosystem MUST be configured +in the relevant checks: + +| Ecosystem Detected | CodeQL Language | SonarCloud | CI Pipeline | Dependency Audit | +|--------------------|----------------|------------|-------------|------------------| +| `package.json` / `package-lock.json` | `javascript-typescript` | JS/TS analysis | npm/pnpm lint, typecheck, test | `npm audit` or `pnpm audit` | +| `go.mod` | `go` | Go analysis | `go vet`, `golangci-lint`, `go test` | `govulncheck` | +| `Cargo.toml` | `rust` (if supported) | Rust analysis | `cargo fmt`, `cargo check`, `cargo test` | `cargo audit` | +| `pyproject.toml` / `requirements.txt` | `python` | Python analysis | pytest, coverage | `pip-audit` | +| `.github/workflows/*.yml` | `actions` | — | — | — | +| `*.tf` (Terraform) | — | — | `terraform validate` | Dependabot security updates | + +Multi-language repos (e.g., TypeScript + Go) MUST configure all applicable +ecosystems in each check. + +#### Additional Settings | Setting | Value | |---------|-------| | **Require branches to be up to date** | Yes (`strict: true`) | | **Enforce for admins** | Yes | -When adding a new repository, determine which CI tools apply to its stack -(see [CI Standards](ci-standards.md)) and add the corresponding checks. +See [CI Standards](ci-standards.md) for workflow templates and patterns. --- From 60274cf669eb1ba27762b4c238a3ac44047cdce4 Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 09:29:41 -0700 Subject: [PATCH 08/11] fix: remove ci-standards.md (belongs in PR #11, not this branch) Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/ci-standards.md | 454 -------------------------------------- 1 file changed, 454 deletions(-) delete mode 100644 standards/ci-standards.md diff --git a/standards/ci-standards.md b/standards/ci-standards.md deleted file mode 100644 index f23d532..0000000 --- a/standards/ci-standards.md +++ /dev/null @@ -1,454 +0,0 @@ -# CI/CD Standards - -Standard CI/CD configurations for all repositories in the **petry-projects** organization. -This document defines the required workflows, quality gates, and patterns that every -repository must implement. - ---- - -## Required Workflows - -Every repository MUST have these workflows. Reusable templates for Dependabot -workflows are in [`standards/workflows/`](workflows/). The CI, CodeQL, -SonarCloud, and Claude Code workflows are documented as patterns below — copy -and adapt the examples to each repo's tech stack. - -### 1. CI Pipeline (`ci.yml`) - -The primary build-and-test workflow. Structure varies by tech stack but must include: - -| Stage | Purpose | Required | -|-------|---------|----------| -| **Lint** | Static analysis / style enforcement | Yes | -| **Format check** | Formatting verification | Yes | -| **Type check** | Type safety (where applicable) | Yes | -| **Unit tests** | Fast, deterministic tests | Yes | -| **Coverage** | Code coverage reporting | Yes | -| **Integration tests** | Backend/API integration | If applicable | -| **E2E tests** | End-to-end functional tests | If applicable | -| **Build / Docker build** | Verify the artifact builds | If applicable | - -**Standard triggers:** - -```yaml -on: - push: - branches: [main] - pull_request: - branches: [main] -``` - -**Standard configuration patterns:** - -```yaml -permissions: {} # Reset top-level; set per-job (see Permissions Policy below) - -concurrency: - group: ci-${{ github.ref }} - cancel-in-progress: true -``` - -### 2. CodeQL Analysis (`codeql.yml`) - -Static Application Security Testing (SAST) via GitHub's CodeQL. - -**Standard configuration:** - -```yaml -on: - push: - branches: [main] - pull_request: - branches: [main] - schedule: - - cron: '25 14 * * 3' # Weekly scan (Wednesday) -``` - -**Language matrix by repo:** - -| Repository | CodeQL Language(s) | -|------------|-------------------| -| **broodly** | `actions` | -| **google-app-scripts** | `javascript-typescript` | -| **TalkTerm** | `python` (pending: `javascript-typescript`) | -| **markets** | `javascript-typescript` | -| **ContentTwin** | `javascript-typescript` (pending) | - -### 3. SonarCloud Analysis (`sonarcloud.yml`) - -Code quality, maintainability, security hotspots, and coverage tracking. - -**Standard configuration:** - -```yaml -name: SonarCloud Analysis - -permissions: {} - -on: - push: - branches: [main] - pull_request: - branches: [main] - -jobs: - sonarcloud: - name: SonarCloud - runs-on: ubuntu-latest - permissions: - contents: read - pull-requests: read - env: - SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} - steps: - - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - with: - fetch-depth: 0 - - name: SonarCloud Scan - if: ${{ env.SONAR_TOKEN != '' }} - uses: SonarSource/sonarqube-scan-action@a31c9398be7ace6bbfaf30c0bd5d415f843d45e9 # v7.0.0 -``` - -**Required secrets:** `SONAR_TOKEN` - -Each repo needs a `sonar-project.properties` file at root with project key and org. - -### 4. Claude Code (`claude.yml`) - -AI-assisted code review via Claude Code Action on PRs. Also responds to -`@claude` mentions in PR comments. - -**Standard configuration:** - -```yaml -name: Claude Code - -on: - pull_request: - branches: [main] - types: [opened, reopened, synchronize] - issue_comment: - types: [created] - pull_request_review_comment: - types: [created] - -permissions: {} - -jobs: - claude: - if: >- - (github.event_name == 'pull_request' && - github.event.pull_request.head.repo.full_name == github.repository) || - (github.event_name == 'issue_comment' && github.event.issue.pull_request && - contains(github.event.comment.body, '@claude') && - contains(fromJson('["OWNER","MEMBER","COLLABORATOR"]'), github.event.comment.author_association)) || - (github.event_name == 'pull_request_review_comment' && - contains(github.event.comment.body, '@claude') && - contains(fromJson('["OWNER","MEMBER","COLLABORATOR"]'), github.event.comment.author_association)) - runs-on: ubuntu-latest - timeout-minutes: 60 - permissions: - contents: read - id-token: write - pull-requests: write - issues: write - steps: - - name: Run Claude Code - if: github.event_name != 'pull_request' || github.event.pull_request.user.login != 'dependabot[bot]' - uses: anthropics/claude-code-action@bee87b3258c251f9279e5371b0cc3660f37f3f77 # v1 - with: - claude_code_oauth_token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }} -``` - -**Required secrets:** `CLAUDE_CODE_OAUTH_TOKEN` - -**Dependabot behavior:** The Claude Code step is skipped for Dependabot PRs (the -`if` condition on the step). The job still runs and reports SUCCESS to satisfy -required status checks. See [AGENTS.md](../AGENTS.md#claude-code-workflow-on-dependabot-prs). - -### 5. Dependabot Auto-Merge (`dependabot-automerge.yml`) - -Automatically approves and squash-merges eligible Dependabot PRs. -See [`workflows/dependabot-automerge.yml`](workflows/dependabot-automerge.yml) -and the [Dependabot Policy](dependabot-policy.md) for full details. - -### 6. Dependency Audit (`dependency-audit.yml`) - -Vulnerability scanning for all package ecosystems. -See [`workflows/dependency-audit.yml`](workflows/dependency-audit.yml) -and the [Dependabot Policy](dependabot-policy.md). - ---- - -## Workflow Patterns by Tech Stack - -### TypeScript / Node.js (npm) - -```yaml -steps: - - uses: actions/checkout@v4 - - uses: actions/setup-node@v4 - with: - node-version: '20' # or 'lts/*' - cache: npm - - run: npm ci - - run: npm run check # lint + format - - run: npm run typecheck # tsc --noEmit - - run: npm test # unit tests + coverage -``` - -**Repos using this pattern:** google-app-scripts, ContentTwin - -### TypeScript / Node.js (pnpm) - -```yaml -steps: - - uses: actions/checkout@v4 - - uses: pnpm/action-setup@v4 - - uses: actions/setup-node@v4 - with: - node-version: 20 - cache: pnpm - - run: pnpm install --frozen-lockfile - - run: pnpm run lint - - run: pnpm run typecheck - - run: pnpm run test -``` - -**Repos using this pattern:** broodly (TypeScript layer) - -### Go - -```yaml -steps: - - uses: actions/checkout@v4 - - uses: actions/setup-go@v5 - with: - go-version: 'stable' # Or pin to specific version (e.g., '1.24') matching go.mod - cache-dependency-path: apps/api/go.sum - - run: go vet ./... - - uses: golangci/golangci-lint-action@v6 - - run: go test ./... -race -coverprofile=coverage.out -``` - -**Repos using this pattern:** broodly (Go API) - -### TypeScript + Electron (npm) - -```yaml -strategy: - matrix: - os: [ubuntu-latest, macos-latest, windows-latest] -steps: - - uses: actions/checkout@v4 - - uses: actions/setup-node@v4 - with: - node-version: 24 - cache: npm - - run: npm ci - - run: npm run typecheck - - run: npm run lint - - run: npm run format:check - - run: npm test - - run: npm run test:coverage -``` - -**Additional jobs for Electron:** -- Mutation testing (`npm run test:mutate`) — `continue-on-error: true` -- E2E tests via Playwright (`npx playwright test`) on macOS — `continue-on-error: true` - -**Repos using this pattern:** TalkTerm - -### Python - -```yaml -steps: - - uses: actions/checkout@v4 - - uses: actions/setup-python@v5 - with: - python-version: '3.x' - # Project-specific: pip install, pytest, etc. -``` - -**Repos using this pattern:** TalkTerm (CodeQL only currently) - ---- - -## Action Pinning Policy - -All GitHub Actions MUST be pinned to a specific commit SHA, not a tag or branch. - -```yaml -# CORRECT — pinned to SHA -- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - -# WRONG — mutable tag -- uses: actions/checkout@v4 -``` - -**Rationale:** SHA pinning prevents supply-chain attacks where a tag is -force-pushed to a malicious commit. The comment after the SHA documents the -version for human readability. - -Dependabot keeps pinned SHAs up to date via the `github-actions` ecosystem -entry in `dependabot.yml`. - -> **Note on examples in this document:** The "Workflow Patterns by Tech Stack" -> section uses tag references (e.g., `@v4`) for readability since those are -> illustrative patterns, not copy-paste templates. The "Required Workflows" -> section above uses SHA-pinned references where possible. When copying any -> example to a repository, always look up the current SHA for each action and -> pin to it with a version comment. - ---- - -## Permissions Policy - -All workflows MUST follow the principle of least privilege: - -```yaml -# Multi-job workflows: reset at top, set per-job -permissions: {} - -jobs: - my-job: - permissions: - contents: read # Only what this job needs -``` - -For single-job workflows, top-level least-privilege permissions are acceptable -(e.g., `permissions: contents: read`) since there is only one job to scope. - -**Common permission sets:** - -| Workflow | Permissions | -|----------|------------| -| CI (build/test) | `contents: read` | -| SonarCloud | `contents: read`, `pull-requests: read` | -| Claude Code | `contents: read`, `id-token: write`, `pull-requests: write`, `issues: write` | -| CodeQL | `actions: read`, `security-events: write`, `contents: read` | -| Dependabot auto-merge | `contents: read`, `pull-requests: read` (+ app token for merge) | - ---- - -## Secrets Required by Repository - -| Secret | Purpose | Repos | -|--------|---------|-------| -| `CLAUDE_CODE_OAUTH_TOKEN` | Claude Code Action authentication | All repos with `claude.yml` | -| `SONAR_TOKEN` | SonarCloud analysis | broodly, markets, ContentTwin, google-app-scripts | -| `APP_ID` | GitHub App for Dependabot auto-merge | All repos with `dependabot-automerge.yml` | -| `APP_PRIVATE_KEY` | GitHub App private key | All repos with `dependabot-automerge.yml` | -| `GCP_PROJECT_ID` | GCP project for container registry | broodly | -| `GCP_WORKLOAD_IDENTITY_PROVIDER` | GCP Workload Identity Federation | broodly | -| `GCP_SERVICE_ACCOUNT` | GCP service account email | broodly | - ---- - -## CI Job Naming Convention - -CI job names become the GitHub status check names that branch protection -references. Use consistent, descriptive names: - -| Pattern | Example | Notes | -|---------|---------|-------| -| Language / tool name | `TypeScript`, `Go`, `SonarCloud` | For multi-language repos | -| `build-and-test` | `build-and-test` | For single-language repos | -| `Analyze` or `Analyze ()` | `Analyze`, `Analyze (Python)` | CodeQL jobs | -| `claude` | `claude` | Claude Code Action | - -These names are referenced in branch protection required status checks. -Changing a job name requires updating the branch protection configuration. - ---- - -## Org-Level Workflows - -The [`.github` repository](https://github.com/petry-projects/.github) contains -org-level workflows that run across all repositories: - -### OpenSSF Scorecard (`org-scorecard.yml`) - -- **Schedule:** Weekly (Monday 9:00 UTC) -- **Purpose:** Security posture scoring for all public repos -- **Behavior:** Creates/updates GitHub Issues with findings, auto-closes resolved findings -- **Skip list:** CII-Best-Practices, Contributors, Fuzzing, Maintained, Packaging, Signed-Releases - ---- - -## CI Auto-Fix Pattern - -Some repositories implement automatic formatting fixes on PRs: - -```yaml -autofix: - needs: build-and-test - if: > - github.event_name == 'pull_request' && - github.event.pull_request.head.repo.full_name == github.repository - runs-on: ubuntu-latest - permissions: - contents: write - steps: - - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - with: - ref: ${{ github.event.pull_request.head.ref }} - - run: npm run format && npm run lint -- --fix - - name: Commit fixes - run: | - if ! git diff --quiet; then - git config user.name "github-actions[bot]" - git config user.email "github-actions[bot]@users.noreply.github.com" - git add -A - git commit -m "chore(ci): apply prettier/eslint auto-fixes" - git push - fi -``` - -**Repos using this pattern:** google-app-scripts - -> **Note:** Auto-fix only runs on same-repo PRs (not forks) since it needs -> write access to the PR branch. - ---- - -## Applying CI to a New Repository - -1. **Determine tech stack** and select the matching workflow patterns above -2. **Create `ci.yml`** with lint, format, typecheck, and test stages -3. **Add `codeql.yml`** with the appropriate language(s) -4. **Add `sonarcloud.yml`** and configure `sonar-project.properties` -5. **Add `claude.yml`** for AI code review -6. **Add `dependabot.yml`** from the appropriate template in [`standards/dependabot/`](dependabot/) -7. **Add `dependabot-automerge.yml`** from [`standards/workflows/`](workflows/) -8. **Add `dependency-audit.yml`** from [`standards/workflows/`](workflows/) -9. **Configure secrets** in the repository settings -10. **Set required status checks** in branch protection (see [GitHub Settings](github-settings.md)) -11. **Pin all action references** to commit SHAs - ---- - -## Current Repository CI Status - -| Repository | CI | CodeQL | SonarCloud | Claude | Dep Auto-merge | Dep Audit | Dependabot Config | -|------------|:--:|:------:|:----------:|:------:|:--------------:|:---------:|:-----------------:| -| **broodly** | Yes | Yes | Yes | Yes | Yes | Yes | Yes | -| **markets** | — | Yes | Yes | Yes | Yes | Yes | Partial (missing npm ecosystem) | -| **google-app-scripts** | Yes | Yes | Yes | Yes | Yes (older pattern) | — | Non-standard (npm limit:10) | -| **TalkTerm** | Yes | — | — | — | — | — | — | -| **ContentTwin** | — | — | Yes | — | — | — | — | -| **bmad-bgreat-suite** | — | — | — | — | — | — | — | - -### Gaps to Address - -- **TalkTerm:** Missing SonarCloud, Claude Code, Dependabot config, auto-merge, dependency audit, CodeQL -- **ContentTwin:** Missing CI pipeline, CodeQL, Claude Code, Dependabot config, auto-merge, dependency audit -- **bmad-bgreat-suite:** Missing all CI workflows (new repo — no branch protection or rulesets either) -- **google-app-scripts:** Missing dependency audit workflow; Dependabot config uses `limit:10` for npm (should be `0` per policy); auto-merge workflow uses older pattern (`--admin` bypass instead of `--auto`) -- **markets:** Missing dedicated CI pipeline; Dependabot config only covers `github-actions` — missing `npm` ecosystem entry - -### Version Inconsistencies - -- **SonarCloud action:** broodly/markets use v7.0.0; ContentTwin/google-app-scripts use v6 -- **CodeQL action:** broodly uses v4; markets uses v3 -- **Claude Code Action:** Different SHA pins across repos (should be aligned) From b232f5d70e79ea5b997e7cf984cfc124609d15fc Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 09:36:44 -0700 Subject: [PATCH 09/11] fix: consolidate secrets documentation, add CLAUDE_CODE_OAUTH_TOKEN - Split secrets into org-level and repo-level sections - Add CLAUDE_CODE_OAUTH_TOKEN to org secrets table - Add SONAR_TOKEN and GCP secrets to repo-level table - Align onboarding note with secrets sections Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 26 +++++++++++++++++--------- 1 file changed, 17 insertions(+), 9 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index e9349df..8ab4c50 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -140,18 +140,25 @@ See [CI Standards](ci-standards.md) for workflow templates and patterns. | **CodeQL** | Static analysis (SAST) via GitHub Actions | Repos with CodeQL workflows | | **Dependabot** | Security updates for dependencies | All repos (see [Dependabot Policy](dependabot-policy.md)) | -### GitHub App Secrets for Auto-Merge +### Organization-Level Secrets -The `dependabot-automerge-petry` app provides the approving review required by -rulesets for automated Dependabot merges. These secrets are configured at the -**organization level** and inherited by all repos: +These secrets are configured at the **organization level** and inherited by +all repos automatically — no per-repo setup needed: | Secret | Level | Purpose | |--------|-------|---------| -| `APP_ID` | Organization | GitHub App ID (app_id: 3167543) | -| `APP_PRIVATE_KEY` | Organization | GitHub App private key | +| `APP_ID` | Organization | GitHub App ID for Dependabot auto-merge (app_id: 3167543) | +| `APP_PRIVATE_KEY` | Organization | GitHub App private key for Dependabot auto-merge | +| `CLAUDE_CODE_OAUTH_TOKEN` | Organization | Authentication for Claude Code Action | -New repositories automatically inherit these secrets — no per-repo configuration needed. +### Repo-Level Secrets + +These must be configured per-repo when the corresponding integration is added: + +| Secret | Purpose | +|--------|---------| +| `SONAR_TOKEN` | SonarCloud analysis authentication | +| GCP secrets (`GCP_PROJECT_ID`, etc.) | Cloud deployment (repos with GCP infrastructure) | --- @@ -186,8 +193,9 @@ When creating a new repository in `petry-projects`: 9. **Connect integrations** — ensure CodeRabbit and SonarCloud (if applicable) are enabled > **Note:** Org-level secrets (`APP_ID`, `APP_PRIVATE_KEY`, `CLAUDE_CODE_OAUTH_TOKEN`) -> are inherited automatically. Repo-specific secrets (e.g., `SONAR_TOKEN`, GCP -> credentials) must be configured per-repo. +> are inherited automatically. Add repo-level secrets (`SONAR_TOKEN`, GCP credentials) +> as needed — see [Organization-Level Secrets](#organization-level-secrets) and +> [Repo-Level Secrets](#repo-level-secrets) above. --- From cb3c70a0b8449510c05d3056ccdb85002fc5a235 Mon Sep 17 00:00:00 2001 From: DJ Date: Sun, 5 Apr 2026 09:42:44 -0700 Subject: [PATCH 10/11] fix: CodeQL rule-based, org-level secrets, remove repo-level section MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - CodeQL definition now focuses on rule: all ecosystems must be configured - Move SONAR_TOKEN to org-level secrets - Remove repo-level secrets section — all standard CI secrets are org-level - Simplify onboarding note Co-Authored-By: Claude Opus 4.6 (1M context) --- standards/github-settings.md | 28 +++++++++++----------------- 1 file changed, 11 insertions(+), 17 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index 8ab4c50..f896049 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -87,7 +87,7 @@ categories are universal. | Check | Required | Check Name(s) | Notes | |-------|----------|---------------|-------| | **SonarCloud** | All repos | `SonarCloud` | Code quality, maintainability, security hotspots | -| **CodeQL** | All repos | `Analyze` or `Analyze ()` | SAST — language(s) match the repo's ecosystems | +| **CodeQL** | All repos | `Analyze` or `Analyze ()` | SAST — all ecosystems present in the repo must be configured | | **Claude Code** | All repos | `claude` | AI code review on every PR | | **CI Pipeline** | All repos | Repo-specific (e.g., `build-and-test`, `TypeScript`, `Go`) | Lint, format, typecheck, test | | **Coverage** | All repos | `coverage` or embedded in CI job | Must meet repo-defined thresholds | @@ -140,25 +140,20 @@ See [CI Standards](ci-standards.md) for workflow templates and patterns. | **CodeQL** | Static analysis (SAST) via GitHub Actions | Repos with CodeQL workflows | | **Dependabot** | Security updates for dependencies | All repos (see [Dependabot Policy](dependabot-policy.md)) | -### Organization-Level Secrets +### Organization-Level Secrets for Standard CI These secrets are configured at the **organization level** and inherited by all repos automatically — no per-repo setup needed: -| Secret | Level | Purpose | -|--------|-------|---------| -| `APP_ID` | Organization | GitHub App ID for Dependabot auto-merge (app_id: 3167543) | -| `APP_PRIVATE_KEY` | Organization | GitHub App private key for Dependabot auto-merge | -| `CLAUDE_CODE_OAUTH_TOKEN` | Organization | Authentication for Claude Code Action | - -### Repo-Level Secrets - -These must be configured per-repo when the corresponding integration is added: - | Secret | Purpose | |--------|---------| +| `APP_ID` | GitHub App ID for Dependabot auto-merge (app_id: 3167543) | +| `APP_PRIVATE_KEY` | GitHub App private key for Dependabot auto-merge | +| `CLAUDE_CODE_OAUTH_TOKEN` | Authentication for Claude Code Action | | `SONAR_TOKEN` | SonarCloud analysis authentication | -| GCP secrets (`GCP_PROJECT_ID`, etc.) | Cloud deployment (repos with GCP infrastructure) | + +Repos with additional infrastructure (e.g., GCP deployment) may require +repo-specific secrets beyond this standard set. --- @@ -192,10 +187,9 @@ When creating a new repository in `petry-projects`: 8. **Enable auto-delete head branches** and **auto-merge** in repo settings 9. **Connect integrations** — ensure CodeRabbit and SonarCloud (if applicable) are enabled -> **Note:** Org-level secrets (`APP_ID`, `APP_PRIVATE_KEY`, `CLAUDE_CODE_OAUTH_TOKEN`) -> are inherited automatically. Add repo-level secrets (`SONAR_TOKEN`, GCP credentials) -> as needed — see [Organization-Level Secrets](#organization-level-secrets) and -> [Repo-Level Secrets](#repo-level-secrets) above. +> **Note:** All standard CI secrets are configured at the org level and inherited +> automatically — see [Organization-Level Secrets](#organization-level-secrets-for-standard-ci). +> No per-repo secret setup is needed for standard CI workflows. --- From be9e0392421a9ce7391294d724d14eac59f058ab Mon Sep 17 00:00:00 2001 From: don-petry <36422719+don-petry@users.noreply.github.com> Date: Sun, 5 Apr 2026 09:54:08 -0700 Subject: [PATCH 11/11] Fix typo in repo-specific secrets note Correct typo in the note about repo-specific secrets. --- standards/github-settings.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/standards/github-settings.md b/standards/github-settings.md index f896049..e16e94d 100644 --- a/standards/github-settings.md +++ b/standards/github-settings.md @@ -152,8 +152,7 @@ all repos automatically — no per-repo setup needed: | `CLAUDE_CODE_OAUTH_TOKEN` | Authentication for Claude Code Action | | `SONAR_TOKEN` | SonarCloud analysis authentication | -Repos with additional infrastructure (e.g., GCP deployment) may require -repo-specific secrets beyond this standard set. +Repos's may require repo-specific secrets beyond this standard set. ---