Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/self-review-pr.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ jobs:
if: |
github.event_name == 'issue_comment' ||
github.event.workflow_run.conclusion == 'success'
uses: docker/cagent-action/.github/workflows/review-pr.yml@f208610469d69f20983cad64c577949a132caa33 # v1.5.3
uses: ./.github/workflows/review-pr.yml
Comment thread
derekmisler marked this conversation as resolved.
permissions:
contents: read # Read repository files and PR diffs
pull-requests: write # Post review comments
Expand Down
275 changes: 275 additions & 0 deletions .github/workflows/test-e2e-reviewer.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,275 @@
name: Test Reviewer E2E (Manual)

on:
workflow_dispatch:
inputs:
pr_number:
description: 'PR number to run the scenario against'
required: true
default: '207'
scenario:
description: 'Scenario to test'
required: true
type: choice
options:
- full-review
- top-level-mention
- inline-mention
default: full-review

permissions:
contents: read

jobs:
full-review:
name: Full Review E2E
if: inputs.scenario == 'full-review'
uses: ./.github/workflows/review-pr.yml
permissions:
contents: read
pull-requests: write
issues: write
id-token: write
checks: write
actions: read
with:
pr-number: ${{ inputs.pr_number }}
secrets:
ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }}
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
GOOGLE_API_KEY: ${{ secrets.GOOGLE_API_KEY }}
AWS_BEARER_TOKEN_BEDROCK: ${{ secrets.AWS_BEARER_TOKEN_BEDROCK }}
XAI_API_KEY: ${{ secrets.XAI_API_KEY }}
NEBIUS_API_KEY: ${{ secrets.NEBIUS_API_KEY }}
MISTRAL_API_KEY: ${{ secrets.MISTRAL_API_KEY }}

top-level-mention:
name: Top-Level Mention E2E
if: inputs.scenario == 'top-level-mention'
runs-on: ubuntu-latest
permissions:
contents: read
id-token: write
steps:
- name: Check if fork PR
id: fork-check
run: |
HEAD_REPO="${{ github.event.pull_request.head.repo.full_name || '' }}"
if [[ "${{ github.event_name }}" == "pull_request" && "$HEAD_REPO" != "${{ github.repository }}" && -n "$HEAD_REPO" ]]; then
echo "⏭️ Skipping - fork PR (secrets not available)"
echo "is_fork=true" >> $GITHUB_OUTPUT
else
echo "is_fork=false" >> $GITHUB_OUTPUT
fi

- name: Checkout code
if: steps.fork-check.outputs.is_fork != 'true'
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

- name: Setup pnpm
if: steps.fork-check.outputs.is_fork != 'true'
uses: pnpm/action-setup@8912a9102ac27614460f54aedde9e1e7f9aec20d # v6.0.5
with:
run_install: false

- name: Setup Node.js
if: steps.fork-check.outputs.is_fork != 'true'
uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e # v6.4.0
with:
node-version: 24
cache: pnpm

- name: Build action
if: steps.fork-check.outputs.is_fork != 'true'
run: pnpm install --frozen-lockfile && pnpm build

- name: Setup credentials
if: steps.fork-check.outputs.is_fork != 'true'
uses: docker/cagent-action/setup-credentials@2a43a3882401f45e3114df7f6d66eca184993a90 # v1.5.2

- name: Write synthetic issue_comment event
if: steps.fork-check.outputs.is_fork != 'true'
run: |
jq -n \
--arg actor "${{ github.actor }}" \
--argjson pr_number "${{ inputs.pr_number }}" \
'{
"action": "created",
"issue": {
"number": $pr_number,
"pull_request": { "url": ("https://api.github.com/repos/docker/cagent-action/pulls/" + ($pr_number | tostring)) }
},
"comment": {
"id": 9999999901,
"body": "@docker-agent this is a manual e2e test — please reply with a brief acknowledgement.",
"user": { "login": $actor, "type": "User" }
},
"repository": {
"owner": { "login": "docker" },
"name": "cagent-action"
},
"sender": { "login": $actor, "type": "User" }
}' > /tmp/test-event-toplevel.json

- name: Run mention-reply handler
if: steps.fork-check.outputs.is_fork != 'true'
id: mention-handler
uses: ./.github/actions/mention-reply
env:
GITHUB_EVENT_PATH: /tmp/test-event-toplevel.json
GITHUB_EVENT_NAME: issue_comment
with:
github-token: ${{ env.GITHUB_APP_TOKEN || github.token }}
org-membership-token: ${{ env.ORG_MEMBERSHIP_TOKEN || github.token }}

- name: Run mention reply
if: steps.fork-check.outputs.is_fork != 'true' && steps.mention-handler.outputs.should-reply == 'true'
id: run-reply
uses: ./review-pr/mention-reply
with:
mention-context: ${{ steps.mention-handler.outputs.prompt }}
owner: ${{ steps.mention-handler.outputs.owner }}
repo: ${{ steps.mention-handler.outputs.repo }}
pr-number: ${{ steps.mention-handler.outputs.pr-number }}
is-inline: ${{ steps.mention-handler.outputs.is-inline }}
in-reply-to-id: ${{ steps.mention-handler.outputs.in-reply-to-id }}
anthropic-api-key: ${{ env.ANTHROPIC_API_KEY_FROM_SSM || secrets.ANTHROPIC_API_KEY }}
openai-api-key: ${{ env.OPENAI_API_KEY_FROM_SSM || secrets.OPENAI_API_KEY }}
github-token: ${{ env.GITHUB_APP_TOKEN || github.token }}
skip-auth: "true"

- name: Report outcome
if: steps.fork-check.outputs.is_fork != 'true'
run: |
echo "should-reply: ${{ steps.mention-handler.outputs.should-reply }}"
echo "owner: ${{ steps.mention-handler.outputs.owner }}"
echo "repo: ${{ steps.mention-handler.outputs.repo }}"
echo "pr-number: ${{ steps.mention-handler.outputs.pr-number }}"
echo "is-inline: ${{ steps.mention-handler.outputs.is-inline }}"
echo "✅ Top-level mention scenario completed (manual run — no assertion)"

inline-mention:
name: Inline Mention E2E
if: inputs.scenario == 'inline-mention'
runs-on: ubuntu-latest
permissions:
contents: read
id-token: write
steps:
- name: Check if fork PR
id: fork-check
run: |
HEAD_REPO="${{ github.event.pull_request.head.repo.full_name || '' }}"
if [[ "${{ github.event_name }}" == "pull_request" && "$HEAD_REPO" != "${{ github.repository }}" && -n "$HEAD_REPO" ]]; then
echo "⏭️ Skipping - fork PR (secrets not available)"
echo "is_fork=true" >> $GITHUB_OUTPUT
else
echo "is_fork=false" >> $GITHUB_OUTPUT
fi

- name: Checkout code
if: steps.fork-check.outputs.is_fork != 'true'
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

- name: Setup pnpm
if: steps.fork-check.outputs.is_fork != 'true'
uses: pnpm/action-setup@8912a9102ac27614460f54aedde9e1e7f9aec20d # v6.0.5
with:
run_install: false

- name: Setup Node.js
if: steps.fork-check.outputs.is_fork != 'true'
uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e # v6.4.0
with:
node-version: 24
cache: pnpm

- name: Build action
if: steps.fork-check.outputs.is_fork != 'true'
run: pnpm install --frozen-lockfile && pnpm build

- name: Setup credentials
if: steps.fork-check.outputs.is_fork != 'true'
uses: docker/cagent-action/setup-credentials@2a43a3882401f45e3114df7f6d66eca184993a90 # v1.5.2

- name: Create anchor review comment
if: steps.fork-check.outputs.is_fork != 'true'
id: create-anchor
env:
GH_TOKEN: ${{ env.GITHUB_APP_TOKEN || github.token }}
PR_NUMBER: ${{ inputs.pr_number }}
run: |
HEAD_SHA=$(gh api "repos/docker/cagent-action/pulls/$PR_NUMBER" --jq '.head.sha')
DIFF_FILE=$(gh api "repos/docker/cagent-action/pulls/$PR_NUMBER/files" --jq '.[0].filename')
echo "Using diff file: $DIFF_FILE"
COMMENT_ID=$(gh api "repos/docker/cagent-action/pulls/$PR_NUMBER/comments" \
-X POST \
--input - <<< $(jq -n \
--arg sha "$HEAD_SHA" \
--arg path "$DIFF_FILE" \
'{"body": "manual e2e test anchor comment — safe to delete", "commit_id": $sha, "path": $path, "side": "RIGHT", "position": 1}') \
--jq '.id')
echo "Created anchor comment ID: $COMMENT_ID"
echo "test_comment_id=$COMMENT_ID" >> $GITHUB_OUTPUT

- name: Write synthetic pull_request_review_comment event
if: steps.fork-check.outputs.is_fork != 'true'
run: |
COMMENT_ID="${{ steps.create-anchor.outputs.test_comment_id }}"
jq -n \
--arg actor "${{ github.actor }}" \
--argjson comment_id "$COMMENT_ID" \
--argjson pr_number "${{ inputs.pr_number }}" \
'{
"action": "created",
"pull_request": { "number": $pr_number },
"comment": {
"id": $comment_id,
"body": "@docker-agent this is a manual e2e test of the inline mention path.",
"path": "README.md",
"line": 1,
"original_line": 1,
"diff_hunk": "@@ -1,1 +1,1 @@\n-old\n+new",
"user": { "login": $actor, "type": "User" }
},
"repository": {
"owner": { "login": "docker" },
"name": "cagent-action"
},
"sender": { "login": $actor, "type": "User" }
}' > /tmp/test-event-inline.json

- name: Run mention-reply handler
if: steps.fork-check.outputs.is_fork != 'true'
id: mention-handler
uses: ./.github/actions/mention-reply
env:
GITHUB_EVENT_PATH: /tmp/test-event-inline.json
GITHUB_EVENT_NAME: pull_request_review_comment
with:
github-token: ${{ env.GITHUB_APP_TOKEN || github.token }}
org-membership-token: ${{ env.ORG_MEMBERSHIP_TOKEN || github.token }}

- name: Run mention reply
if: steps.fork-check.outputs.is_fork != 'true' && steps.mention-handler.outputs.should-reply == 'true'
id: run-reply
uses: ./review-pr/mention-reply
with:
mention-context: ${{ steps.mention-handler.outputs.prompt }}
owner: ${{ steps.mention-handler.outputs.owner }}
repo: ${{ steps.mention-handler.outputs.repo }}
pr-number: ${{ steps.mention-handler.outputs.pr-number }}
is-inline: ${{ steps.mention-handler.outputs.is-inline }}
in-reply-to-id: ${{ steps.mention-handler.outputs.in-reply-to-id }}
anthropic-api-key: ${{ env.ANTHROPIC_API_KEY_FROM_SSM || secrets.ANTHROPIC_API_KEY }}
openai-api-key: ${{ env.OPENAI_API_KEY_FROM_SSM || secrets.OPENAI_API_KEY }}
github-token: ${{ env.GITHUB_APP_TOKEN || github.token }}
skip-auth: "true"

- name: Report outcome
Comment thread
derekmisler marked this conversation as resolved.
if: steps.fork-check.outputs.is_fork != 'true'
run: |
echo "should-reply: ${{ steps.mention-handler.outputs.should-reply }}"
echo "is-inline: ${{ steps.mention-handler.outputs.is-inline }}"
echo "in-reply-to-id: ${{ steps.mention-handler.outputs.in-reply-to-id }}"
echo "✅ Inline mention scenario completed (manual run — no assertion)"
Loading
Loading