Skip to content

OSAC-1774: Add GitHub Action for automated EP review via agentic-ci - #89

Merged
openshift-merge-bot[bot] merged 2 commits into
osac-project:mainfrom
ItzikEzra-rh:feat/ep-review-gh-action
Jul 5, 2026
Merged

openshift-merge-bot[bot] merged 2 commits into
osac-project:mainfrom
ItzikEzra-rh:feat/ep-review-gh-action

Conversation

@ItzikEzra-rh

@ItzikEzra-rh ItzikEzra-rh commented Jul 2, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Adds a GitHub Action that automatically reviews PRDs and design docs when PRs are opened or updated.

  • Triggers on PRs containing prd.md or design.md
  • Uses agentic-ci (Podman backend) + Claude Code for AI review
  • Routes to prd-review skill (PRDs) or ep-review skill (designs) from osac-workspace
  • Posts structured review comment with rubric scores + findings
  • Applies rfe-creator-auto-reviewed label after review

Files

  • .github/workflows/ep-review.yml — workflow definition
  • .github/scripts/ep_review.py — entry point
  • .github/scripts/ep_hooks.py — agentic-ci hooks (prompt, context, verdict, comment posting)
  • .github/scripts/ep_skill_config.py — SkillConfig builder

Shadow mode

Starts with EP_REVIEW_SHADOW=true (set as repo variable). Reviews run but no comments are posted until verified.

Required secrets

  • GCP_SA_KEY — GCP service account key (base64, for Vertex AI)
  • GCP_PROJECT — Vertex AI project ID
  • GCP_REGION — Vertex AI region

Part of OSAC-1773

Summary by CodeRabbit

  • New Features

    • Added an automated EP review workflow for pull requests that update proposal or design documents.
    • Reviews now generate a structured comment on the PR and can apply an “reviewed” label.
    • Added support for a non-posting shadow mode and saved review artifacts for later inspection.
  • Bug Fixes

    • Improved handling of review scores and verdict data, including validation and automatic score total recalculation when needed.

Adds a GitHub Action that triggers on PRs containing prd.md or design.md.
Uses agentic-ci with Podman backend to run Claude Code review against
the prd-review or ep-review skill from osac-workspace.

Files:
- .github/workflows/ep-review.yml — workflow triggered on PR events
- .github/scripts/ep_review.py — entry point: detects skill, runs review
- .github/scripts/ep_hooks.py — agentic-ci hooks (context, prompt, verdict, comment)
- .github/scripts/ep_skill_config.py — SkillConfig builder

Starts in shadow mode (EP_REVIEW_SHADOW=true) — reviews run but
no comments are posted until verified.

Requires secrets: GCP_SA_KEY, GCP_PROJECT, GCP_REGION

Part of OSAC-1773

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@openshift-ci
openshift-ci Bot requested review from eliorerz and maorfr July 2, 2026 09:45
@coderabbitai

coderabbitai Bot commented Jul 2, 2026 •

Copy link
Copy Markdown

Review Change Stack

Walkthrough

This PR introduces an automated Enhancement Proposal (EP) review GitHub Action. It adds ep_hooks.py implementing PR gating, context writing, prompt building, verdict validation, and comment/label posting; ep_review.py as the orchestration entry point; ep_skill_config.py wiring hooks into an agentic-ci SkillConfig; and a new ep-review.yml workflow triggering on prd.md/design.md changes.

Changes

EP Review Automation

Layer / File(s) Summary
EPHooks core: gating, context, prompts
.github/scripts/ep_hooks.py
Constructor, gh CLI helper, text sanitizer, check_pr_state (dedupe by head SHA), write_pr_context (diff/template/prompt/meta files), and build_prompt (prd-review vs design prompts with verdict schema).
EPHooks verdict handling and comment posting
.github/scripts/ep_hooks.py
load_verdict, validate_scores (integer range checks, total recompute), apply_labels (builds markdown review comment, PATCH/POST via gh, applies reviewed label), and format_cost utility.
ep_review.py entry point
.github/scripts/ep_review.py
Fetches changed files, detects skill (prd-review/ep-review), builds ticket payload, initializes EPHooks, runs agentic_ci.skill.run_skill with shadow-mode support, and falls back to a dry-run context write if agentic-ci is unavailable.
Skill config builder
.github/scripts/ep_skill_config.py
build_skill_config imports SkillConfig from agentic_ci.skill and wires hook callbacks plus fixed backend/container/retry parameters, raising ImportError if unavailable.
EP Review workflow
.github/workflows/ep-review.yml
New workflow triggered on prd.md/design.md changes: checkout, Python 3.12 setup, skills clone, GCP credential setup, script execution with env vars, and artifact upload of verdict/context.

Estimated code review effort: 3 (Moderate) | ~30 minutes

Sequence Diagram(s)

sequenceDiagram
  participant GitHub as GitHub Actions
  participant Script as ep_review.py
  participant Hooks as EPHooks
  participant GH as gh CLI

  GitHub->>Script: trigger on PR (prd.md/design.md change)
  Script->>GH: fetch changed files, PR details
  Script->>Script: detect_skill, build ticket
  Script->>Hooks: check_pr_state
  Hooks->>GH: check existing bot comment
  Script->>Hooks: build_prompt / write_pr_context
  Script->>Script: run_skill (agentic-ci) -> verdict.json
  Script->>Hooks: validate_scores, apply_labels
  Hooks->>GH: PATCH/POST comment, add reviewed label
Loading

Estimated code review effort: 3 (Moderate) | ~30 minutes

🚥 Pre-merge checks | ✅ 10 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Ai-Attribution ⚠️ Warning PR commit uses Co-Authored-By for Claude Opus 4.6, and no Assisted-by/Generated-by Red Hat trailer is present. Replace the AI co-author line with an Assisted-by or Generated-by trailer, and avoid Co-Authored-By for AI tools.
✅ Passed checks (10 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
No-Hardcoded-Secrets ✅ Passed No hardcoded secrets, credential URLs, private keys, or secret-like literal assignments were found in the added workflow/scripts.
No-Weak-Crypto ✅ Passed No weak ciphers/hashes, custom crypto, or secret comparisons were found in the PR files; only secret env var wiring appears in the workflow.
No-Injection-Vectors ✅ Passed No SQL/eval/pickle/yaml/os.system/shell=True/dangerous HTML paths found; subprocess calls use arg lists, and jq filters only interpolate fixed constants.
Container-Privileges ✅ Passed No container/K8s manifest in the PR sets privileged, hostPID/network/IPC, SYS_ADMIN, root, or allowPrivilegeEscalation.
No-Sensitive-Data-In-Logs ✅ Passed No added logs print secrets, tokens, PII, hostnames, or customer data; messages only emit PR number/SHA, file names, scores, and generic errors.
Title check ✅ Passed The title clearly matches the main change: a new GitHub Action for automated EP review using agentic-ci.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 17

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.github/scripts/ep_hooks.py:
- Around line 27-34: The _gh helper currently swallows GitHub CLI failures by
printing stderr and returning an empty string, which lets callers of ep_hooks.py
continue as if comment/label operations succeeded. Update _gh to fail closed by
raising on nonzero subprocess.run return codes, or add an explicit opt-in
non-throwing mode only for probe-style callers; make sure the behavior is
enforced at the _gh method so side-effect operations do not silently succeed on
gh errors.
- Around line 93-138: The _prd_prompt and _design_prompt builders currently tell
the reviewer to read .context/pr-diff.txt, .context/template.md, and
.context/skill-prompt.md without explicitly separating instructions from
PR-authored content. Update these prompts to add a clear prompt-injection
boundary that says all diff/template/context contents are data only and any
instructions found inside them must be ignored, while keeping the existing
verdict.json schema and scoring guidance intact.
- Around line 200-203: The posted review comment built in ep_hooks.py is missing
the reviewed commit SHA, so the existing “already reviewed” check in
check_pr_state cannot match it reliably. Update the comment body construction
around the lines array in the comment-posting flow to include the current head
SHA (the same head[:8] value used by check_pr_state), preferably in the header
or metadata line alongside the verdict. Make sure the SHA is emitted every time
the review comment is created so the duplicate-review gate can detect it
consistently.
- Around line 154-173: The validate_scores method currently sums raw scores even
when invalid values or unexpected rubric keys are present, which can crash the
post-gate or produce a misleading verdict. Update validate_scores to first
verify the scores dict contains exactly the expected rubric keys for the ticket,
and only then validate each value is an int in range before computing the total.
Use the validate_scores function and its scores/verdict handling to keep the
existing error collection and only write verdict.json after the rubric key set
and values are confirmed valid.

In @.github/scripts/ep_review.py:
- Around line 39-47: The detect_skill() logic only returns the first matching
skill, so when both prd.md and design.md are present the ep-review path is
skipped. Update detect_skill() to detect both doc types and return all matching
skills, then adjust the caller to execute each returned skill (or explicitly
reject mixed inputs if that is the intended behavior). Use the detect_skill()
function and its current prd-review/ep-review selection logic as the main place
to fix this.
- Around line 24-36: The changed-files lookup in gh/get_changed_files is
swallowing api failures by returning an empty list, which makes main treat auth
or API errors as “No files changed in PR.” Update gh to fail loudly when
subprocess.run returns a nonzero code, and have get_changed_files propagate that
failure instead of converting it to [] so main can exit non-successfully; use
the existing gh and get_changed_files symbols to keep the error path consistent.
- Around line 135-142: The ImportError fallback in ep_review.py currently turns
a missing agentic-ci dependency into a silent dry-run, which should only happen
locally. Update the except ImportError path in the main review flow to check
GITHUB_ACTIONS (or equivalent CI detection): keep hooks.write_pr_context and the
dry-run print only when not running in GitHub Actions, and when GITHUB_ACTIONS
is set, fail the workflow immediately with a clear error instead of continuing.
Use the existing import/entrypoint around agentic-ci and hooks.write_pr_context
to place this guard.
- Around line 75-93: The ep_review.py flow currently builds the PR payload
without checking whether the workflow run is stale, so add a guard after
fetching PR data with gh and before creating the ticket: compare the live
pr["headRefOid"] against PR_HEAD_SHA (or the provided head_sha fallback) and
abort the review/posting path when they differ. Use the existing gh(),
pr_raw/json.loads, and ticket construction block to place the check so outdated
runs do not continue.

In @.github/scripts/ep_skill_config.py:
- Line 28: The container_image setting in ep_skill_config should not use the
mutable claude-runner:latest tag. Update the image reference to the pinned
digest form for the claude-runner entry so the execution environment stays fixed
and reproducible. Locate the container_image assignment in the script and
replace the current tag-based reference with the provided sha256 digest.
- Line 9: The build_skill_config helper has an unused skill_path parameter that
should be removed. Update build_skill_config() to accept only the values it
actually uses, then adjust its call site in EPHooks.write_pr_context to stop
passing the redundant path because the skill path is already handled via
ticket["_skill_path"]. Make sure any references to build_skill_config stay
consistent after the signature change.

In @.github/workflows/ep-review.yml:
- Around line 49-57: The ep-review workflow currently uploads retained
verdict/context artifacts in the Upload verdict artifacts step without any
signing or attestation. Add a Sigstore/cosign attestation/signing step for the
artifacts produced by this job, and wire it into the existing workflow around
the Upload verdict artifacts action so retained outputs are signed before being
published or consumed.
- Around line 30-31: The skills repository clone in the workflow is using the
default branch, which can change behavior outside this PR. Update the Clone
skills repo step in ep-review.yml to fetch a specific reviewed commit SHA for
/opt/skills instead of cloning HEAD, so the workflow uses a pinned revision.
Keep the change localized to the git clone step and ensure the selected commit
is explicit and reproducible.
- Around line 19-23: The workflow uses mutable action tags in the ep-review job,
so update each affected `uses:` entry in the GitHub Actions workflow to a full
40-character commit SHA instead of `@v4` or `@v5`. Locate the action references
for `actions/checkout` and `actions/setup-python`, and replace their version
tags with reviewed pinned SHAs while keeping the rest of the job unchanged.
- Around line 3-8: Add PR-scoped concurrency to the ep-review workflow so only
the latest run for a given pull request stays active and older synchronize runs
are cancelled. Update the workflow near the existing pull_request trigger in
ep-review.yml by adding a concurrency block keyed to the PR number or equivalent
unique PR identifier, and set cancel-in-progress so duplicate review runs do not
overlap.
- Around line 13-16: Reduce the GitHub token scope in the workflow permissions
block by changing the permissions used by the ep-review workflow so pull request
access is read-only while keeping issues as write. Update the permissions
section in the workflow definition that currently includes contents,
pull-requests, and issues so the review job still can read PR diffs but only
uses Issues APIs for comments and labels, with no pull-requests write access.
- Around line 19-47: The EP review job is executing
`.github/scripts/ep_review.py` from the checked-out PR/merge ref while sensitive
credentials are available. Update the workflow to run trusted automation code
from the base branch instead of the PR workspace, and have that script fetch PR
content via the API rather than reading potentially attacker-modified files. Use
the existing `Run EP review` step and `.github/scripts/ep_review.py` as the key
locations to harden.
- Around line 27-28: The Install dependencies step in the EP review workflow is
pulling unpinned packages at runtime, so replace the ad hoc pip install in the
workflow with installation from a locked requirements file that pins exact
versions and hashes. Update the workflow around the Install dependencies and Run
EP review steps to use the locked file, then add a dependency audit step before
Run EP review to verify the installed Python packages are safe and reproducible.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: osac-project/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: 0ff8cf15-5ed1-40af-a7ce-1aa0791d68a1

📥 Commits

Reviewing files that changed from the base of the PR and between fb2a1e1 and 504bc40.

📒 Files selected for processing (4)
  • .github/scripts/ep_hooks.py
  • .github/scripts/ep_review.py
  • .github/scripts/ep_skill_config.py
  • .github/workflows/ep-review.yml

Comment thread .github/scripts/ep_hooks.py Outdated
Comment thread .github/scripts/ep_hooks.py
Comment thread .github/scripts/ep_hooks.py
Comment thread .github/scripts/ep_hooks.py
Comment thread .github/scripts/ep_review.py
Comment thread .github/workflows/ep-review.yml Outdated
Comment thread .github/workflows/ep-review.yml Outdated
Comment thread .github/workflows/ep-review.yml Outdated
Comment on lines +30 to +31
- name: Clone skills repo
run: git clone --depth 1 https://github.com/osac-project/osac-workspace /opt/skills

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🔒 Security & Privacy | 🟠 Major | ⚡ Quick win

Pin the skills repository revision.

Cloning the default branch makes prompt/skill behavior change outside this PR’s review. Fetch a reviewed commit SHA for /opt/skills.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ep-review.yml around lines 30 - 31, The skills repository
clone in the workflow is using the default branch, which can change behavior
outside this PR. Update the Clone skills repo step in ep-review.yml to fetch a
specific reviewed commit SHA for /opt/skills instead of cloning HEAD, so the
workflow uses a pinned revision. Keep the change localized to the git clone step
and ensure the selected commit is explicit and reproducible.

Comment thread .github/workflows/ep-review.yml Outdated
@ItzikEzra-rh
ItzikEzra-rh force-pushed the feat/ep-review-gh-action branch from 58e18b9 to b4fe733 Compare July 2, 2026 10:26
@ItzikEzra-rh

Copy link
Copy Markdown
Contributor Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented Jul 2, 2026 •

Copy link
Copy Markdown
✅ Action performed

Review finished.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@ItzikEzra-rh
ItzikEzra-rh force-pushed the feat/ep-review-gh-action branch 4 times, most recently from ada3962 to 426d4b4 Compare July 2, 2026 11:38
1. SHA in comment body — include head SHA for dedup check
2. _gh error handling — raise on failure for write ops (check=True)
3. detect_skill returns all matches — PRs with both prd+design get both reviews
4. Stale run guard — abort if live headRefOid differs from trigger SHA
5. ImportError fails in CI — only dry-run locally
6. Concurrency group — cancel older runs on same PR
7. Prompt injection boundary — context files treated as data only
8. Pin action versions to commit SHAs
9. Pin dependencies via requirements.txt
10. validate_scores checks expected rubric keys
11. Remove unused skill_path param from build_skill_config

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@ItzikEzra-rh
ItzikEzra-rh force-pushed the feat/ep-review-gh-action branch from 426d4b4 to f684adf Compare July 2, 2026 11:40

@maorfr maorfr left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

/lgtm

@openshift-ci

openshift-ci Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: ItzikEzra-rh, maorfr

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@openshift-ci openshift-ci Bot added the approved label Jul 2, 2026
@ItzikEzra-rh ItzikEzra-rh changed the title Add GitHub Action for automated EP review via agentic-ci OSAC-1774: Add GitHub Action for automated EP review via agentic-ci Jul 5, 2026
@openshift-ci-robot

openshift-ci-robot commented Jul 5, 2026 •

Copy link
Copy Markdown

@ItzikEzra-rh: This pull request references OSAC-1774 which is a valid jira issue.

Warning: The referenced jira issue has an invalid target version for the target branch this PR targets: expected the story to target the "5.0.0" version, but no target version was set.

Details

In response to this:

Summary

Adds a GitHub Action that automatically reviews PRDs and design docs when PRs are opened or updated.

  • Triggers on PRs containing prd.md or design.md
  • Uses agentic-ci (Podman backend) + Claude Code for AI review
  • Routes to prd-review skill (PRDs) or ep-review skill (designs) from osac-workspace
  • Posts structured review comment with rubric scores + findings
  • Applies rfe-creator-auto-reviewed label after review

Files

  • .github/workflows/ep-review.yml — workflow definition
  • .github/scripts/ep_review.py — entry point
  • .github/scripts/ep_hooks.py — agentic-ci hooks (prompt, context, verdict, comment posting)
  • .github/scripts/ep_skill_config.py — SkillConfig builder

Shadow mode

Starts with EP_REVIEW_SHADOW=true (set as repo variable). Reviews run but no comments are posted until verified.

Required secrets

  • GCP_SA_KEY — GCP service account key (base64, for Vertex AI)
  • GCP_PROJECT — Vertex AI project ID
  • GCP_REGION — Vertex AI region

Part of OSAC-1773

Summary by CodeRabbit

  • New Features

  • Added an automated EP review workflow for pull requests that update proposal or design documents.

  • Reviews now generate a structured comment on the PR and can apply an “reviewed” label.

  • Added support for a non-posting shadow mode and saved review artifacts for later inspection.

  • Bug Fixes

  • Improved handling of review scores and verdict data, including validation and automatic score total recalculation when needed.

Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the openshift-eng/jira-lifecycle-plugin repository.

@openshift-merge-bot
openshift-merge-bot Bot merged commit 077a4f1 into osac-project:main Jul 5, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants