⚙️ Workflows¶
Council ships with three GitHub Actions workflows. Which one you use depends on who opened the PR, which provider key you want to use, and whether the target repo vendors Council source.
🔀 Quick Decision Guide¶
Who opened the PR?
│
┌────┴──────┐
│ │
You / your team External / fork contributor
│ │
▼ ▼
council-review.yml council-byok.yml
(auto, on PR open) (manual, workflow_dispatch)
For required gates across your own TS/JS repos, use council-openai-gate.yml.
Generate only that workflow with `council init --workflow-profile openai-gate`.
Action Pinning And Runner Compatibility¶
Council's checked-in and generated workflows pin official GitHub Actions to immutable commit SHAs with readable release comments. The current pins use Node.js 24 action releases.
GitHub-hosted runners are updated automatically. For self-hosted runners, use
Actions Runner v2.327.1
or later. Authenticated Git commands launched from a container action with
actions/checkout v6 require
v2.329.0 or later.
Do not replace the immutable pins with moving major tags.
Deterministic Quality Workflow¶
This repository also runs .github/workflows/quality.yml on pull requests and
pushes to main. It does not require model-provider keys and provides the
ordinary deterministic evidence that must sit beside Council review:
- Full pytest suite on Python 3.12 and 3.13.
- Ruff across the repository.
- Strict MkDocs build.
- Package wheel build.
For this repository, branch protection should require these stable checks after their first successful run:
Tests (Python 3.12)Tests (Python 3.13)Lint, docs, and packagecouncil-review
Council is the evidence-based review gate. Deterministic CI proves the code, docs, and package still build and test as expected. Neither replaces the other.
📊 Side-by-Side Comparison¶
council-review.yml |
council-byok.yml |
|
|---|---|---|
| Trigger | pull_request (automatic) |
workflow_dispatch (manual) |
| Secrets access | Repository OPENAI_API_KEY or GOOGLE_API_KEY secret |
Fork/repo GOOGLE_API_KEY secret that you supply |
| Fork PRs | ⚠️ Skips LLM step (no secrets) | ✅ Full review (you trigger it) |
| Inputs | None — runs on the PR branch | base_ref, upstream_repo, audience |
| Input validation | N/A | ✅ Branch ref + repo format validated |
| Artifacts | council-report.json |
council-report.json + council-review.md |
| Use case | Every PR from your own branches | Fork PRs, external contributors, targeted re-runs |
council-openai-gate.yml |
|
|---|---|
| Trigger | pull_request (automatic) |
| Secrets access | Repository OPENAI_API_KEY secret |
| Fork PRs | Fails closed when the key is unavailable |
| Install path | Installs Council from COUNCIL_INSTALL_SPEC pinned to v0.3.0 by default |
| Chair model | openai/gpt-5.5 with chair_reasoning_effort = "medium" |
| Use case | Required branch-protection gate for other repos |
🔄 PR Workflow — council-review.yml¶
This is the always-on review gate. It fires automatically when a PR is opened or updated.
What it does¶
- Checks out the PR branch
- Checks whether
OPENAI_API_KEYorGOOGLE_API_KEYis available - If
OPENAI_API_KEYis available: writes a temporary OpenAI config and runs the full 5-stage pipeline, including Gate Zero - Otherwise, if
GOOGLE_API_KEYis available: writes a temporary Gemini config and runs the same pipeline - If neither secret is available (fork PR or missing repo secret): skips LLM, uploads a report explaining the skip
- Posts a PR summary with deterministic next steps and accepted-finding guidance
- Uploads
council-report.jsonas a workflow artifact
Where to find the artifact¶
Fork PRs
Fork PRs cannot access repository secrets — this is GitHub's security model, not a Council bug. The PR workflow detects missing LLM provider keys, skips the LLM step, and uploads a council-report.json explaining the skip. Do not work around this. Use council-byok.yml with a fork-local GOOGLE_API_KEY to review fork contributor PRs.
🔑 BYOK Workflow — council-byok.yml¶
This is the manual, key-controlled review workflow. You trigger it explicitly
from the Actions tab. It is also pinned to Gemini and fails fast if
GOOGLE_API_KEY is not configured in the repository or fork where it runs.
Workflow dispatch inputs¶
| Input | Required | Description |
|---|---|---|
base_ref |
✅ Yes | The base branch to diff against (e.g. main) |
upstream_repo |
❌ Optional | Full owner/repo if reviewing a fork (e.g. contributor/myrepo) |
audience |
❌ Optional | Output audience: developer (default) or owner |
Input validation¶
Before running, the BYOK workflow validates:
base_refpassesgit check-ref-format(prevents injection via malformed ref)upstream_repomatchesowner/repoformat if provided (prevents redirect attacks)- All file reads are contained within the repo root via
is_relative_to()(prevents path traversal)
Use restricted keys
The BYOK workflow uses your repository secrets directly. Use inference-only API keys with no billing or admin access. See Security → API Key Hardening.
How to trigger¶
The Gemini workflows use gemini/gemini-2.5-flash in CI, set
reviewer_timeout_seconds = 360, and run reviewers sequentially with
reviewer_concurrency = 1 to reduce model timeout/rate-limit noise.
Required OpenAI PR Gate — council-openai-gate.yml¶
Use this workflow when you want Council to be a required PR check across your TS/JS repositories without vendoring the Council source into each repo.
What it does¶
- Checks out the PR branch with full history
- Installs Council from
COUNCIL_INSTALL_SPEC - Fails closed if
OPENAI_API_KEYis missing - Writes a temporary OpenAI CI config with:
- Chair:
openai/gpt-5.5 - Chair reasoning effort:
medium - Reviewers: OpenAI GPT-5.2 family
- TS/JS analyzers enabled
- Runs
council review --ci --github-pr --branch "$BASE_REF"withBASE_REFsupplied from the PR base ref - Uploads
council-report.json
The scaffold defaults COUNCIL_INSTALL_SPEC to v0.3.0. Keep that value
pinned to a release tag or commit SHA before making the check required across
many repos; do not use a moving branch such as main for protected-branch
rollout.
For a full rollout checklist and language-support matrix, see the Adoption Guide. For coding-agent repair loops that consume Council outputs, see the Agent Loop guide.
Before broad external rollout, run the manual Release Smoke workflow in this
repo. It verifies that a release tag or commit SHA can install Council and
generate an OpenAI gate scaffold pinned to that same ref.
📦 Artifacts Reference¶
| Artifact | File | Workflow | Contents |
|---|---|---|---|
council-report |
council-report.json |
All workflows | Machine-readable Chair verdict, findings, reviewer health, degraded reasons, and transport notes |
council-report |
council-review.md |
BYOK only | Human-readable markdown review with next steps and accepted-finding fix guidance (developer or owner format) |
See the JSON Contract for automation-safe parsing rules.
Finding your artifacts¶
Getting council-review.md from a PR workflow run¶
The PR workflow currently only uploads council-report.json. To get the markdown review:
Option A — Run the BYOK workflow against the same branch
Option B — Run locally:
💻 Local Workflow¶
Local runs are always advisory by default — they never block a push.
| Mode | Command | Blocks on FAIL? |
|---|---|---|
| Advisory | council review --branch main |
No |
| Advisory + JSON | council review --branch main --output-json report.json |
No |
| Advisory + Markdown | council review --branch main --output-md review.md |
No |
| CI mode | council review --ci --branch main |
Yes |
CI mode (--ci) exits non-zero on FAIL. PASS WITH WARNINGS always exits zero.
⏩ Related Pages¶
- Getting Started — install, init, first review, adding secrets
- Agent Loop — use Council as feedback for Codex, Claude Code, OpenClaw, and similar agents
- Security — BYOK threat model, input validation details, fork PR policy
- Design — the 5-stage pipeline these workflows invoke