Skip to content

Commit d89e3d7

Browse files
authored
Create agent-docusarus-dev.yml
1 parent 026f986 commit d89e3d7

File tree

1 file changed

+256
-0
lines changed

1 file changed

+256
-0
lines changed
Lines changed: 256 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,256 @@
1+
name: Claude Code Documentation Review
2+
3+
on:
4+
# Trigger on pull requests to main or dev branch
5+
pull_request:
6+
branches:
7+
- main
8+
- dev
9+
paths-ignore:
10+
- '**.md'
11+
- '**.mdx'
12+
13+
# Trigger on issue comments (for tagging)
14+
issue_comment:
15+
types: [created]
16+
17+
# Trigger on PR review comments
18+
pull_request_review_comment:
19+
types: [created]
20+
21+
jobs:
22+
claude-review:
23+
# Only run if it's a PR or if the comment contains the trigger phrase
24+
if: |
25+
github.event_name == 'pull_request' ||
26+
(github.event_name == 'issue_comment' && contains(github.event.comment.body, '@claude')) ||
27+
(github.event_name == 'pull_request_review_comment' && contains(github.event.comment.body, '@claude'))
28+
29+
runs-on: ubuntu-latest
30+
31+
permissions:
32+
contents: read
33+
pull-requests: write
34+
issues: write
35+
36+
steps:
37+
- name: Checkout code
38+
uses: actions/checkout@v4
39+
with:
40+
fetch-depth: 0
41+
42+
- name: Fetch system prompt from private repo
43+
id: fetch-prompt
44+
env:
45+
GH_TOKEN: ${{ secrets.NETWRIX_PROMPT_REPO_TOKEN || secrets.GITHUB_TOKEN }}
46+
run: |
47+
# Fetch the system prompt file from the private repository
48+
echo "Fetching system prompt from netwrix/action-agent-prompts..."
49+
50+
RESPONSE=$(curl -s -w "\n%{http_code}" \
51+
-H "Authorization: token $GH_TOKEN" \
52+
-H "Accept: application/vnd.github.v3.raw" \
53+
https://api.github.com/repos/netwrix/action-agent-prompts/contents/docs-dev.md?ref=main)
54+
55+
HTTP_CODE=$(echo "$RESPONSE" | tail -n1)
56+
CONTENT=$(echo "$RESPONSE" | head -n-1)
57+
58+
if [ "$HTTP_CODE" != "200" ]; then
59+
echo "Failed to fetch system prompt file (HTTP $HTTP_CODE)"
60+
echo "Response: $CONTENT"
61+
exit 1
62+
fi
63+
64+
# Save the content to a file
65+
echo "$CONTENT" > /tmp/system-prompt.md
66+
67+
# Verify the file was created and has content
68+
if [ ! -s /tmp/system-prompt.md ]; then
69+
echo "System prompt file is empty"
70+
exit 1
71+
fi
72+
73+
echo "System prompt fetched successfully"
74+
echo "File size: $(wc -c < /tmp/system-prompt.md) bytes"
75+
76+
- name: Determine trigger context
77+
id: context
78+
run: |
79+
if [[ "${{ github.event_name }}" == "pull_request" ]]; then
80+
echo "is_pr=true" >> $GITHUB_OUTPUT
81+
echo "is_comment=false" >> $GITHUB_OUTPUT
82+
echo "trigger_type=pull_request" >> $GITHUB_OUTPUT
83+
else
84+
echo "is_pr=false" >> $GITHUB_OUTPUT
85+
echo "is_comment=true" >> $GITHUB_OUTPUT
86+
echo "trigger_type=${{ github.event_name }}" >> $GITHUB_OUTPUT
87+
fi
88+
89+
- name: Extract comment prompt (if triggered by comment)
90+
id: extract-prompt
91+
if: steps.context.outputs.is_comment == 'true'
92+
run: |
93+
# Extract the comment after the trigger phrase
94+
COMMENT="${{ github.event.comment.body }}"
95+
# Remove @claude and trim whitespace
96+
PROMPT=$(echo "$COMMENT" | sed 's/@claude//' | sed 's/^[[:space:]]*//;s/[[:space:]]*$//')
97+
98+
# If prompt is empty after removing trigger, provide a default
99+
if [ -z "$PROMPT" ]; then
100+
PROMPT="Please review the changes in this PR and provide feedback on documentation-related aspects."
101+
fi
102+
103+
echo "comment_prompt<<EOF" >> $GITHUB_OUTPUT
104+
echo "$PROMPT" >> $GITHUB_OUTPUT
105+
echo "EOF" >> $GITHUB_OUTPUT
106+
107+
- name: Check for important file changes
108+
id: check-files
109+
if: steps.context.outputs.is_pr == 'true'
110+
run: |
111+
# Get list of changed files
112+
CHANGED_FILES=$(git diff --name-only origin/${{ github.base_ref }}...HEAD || git diff --name-only HEAD~1)
113+
114+
# Check if docusaurus.config.js or sidebar files were modified
115+
IMPORTANT_FILES=$(echo "$CHANGED_FILES" | grep -E "(docusaurus\.config\.js|.*sidebar.*\.js)" || true)
116+
117+
# Check for any non-markdown changes
118+
NON_MD_FILES=$(echo "$CHANGED_FILES" | grep -v -E "\.(md|mdx)$" || true)
119+
120+
if [ -n "$IMPORTANT_FILES" ]; then
121+
echo "has_important_changes=true" >> $GITHUB_OUTPUT
122+
echo "### 🎯 Important Documentation Files Changed" >> $GITHUB_STEP_SUMMARY
123+
echo '```' >> $GITHUB_STEP_SUMMARY
124+
echo "$IMPORTANT_FILES" >> $GITHUB_STEP_SUMMARY
125+
echo '```' >> $GITHUB_STEP_SUMMARY
126+
else
127+
echo "has_important_changes=false" >> $GITHUB_OUTPUT
128+
fi
129+
130+
if [ -n "$NON_MD_FILES" ]; then
131+
echo "### 📝 Non-Markdown Files Changed" >> $GITHUB_STEP_SUMMARY
132+
echo '```' >> $GITHUB_STEP_SUMMARY
133+
echo "$NON_MD_FILES" >> $GITHUB_STEP_SUMMARY
134+
echo '```' >> $GITHUB_STEP_SUMMARY
135+
fi
136+
137+
- name: Prepare review prompt
138+
id: prepare-prompt
139+
run: |
140+
if [[ "${{ steps.context.outputs.is_pr }}" == "true" ]]; then
141+
# For PRs, create a comprehensive review prompt
142+
PROMPT="You are reviewing a pull request for a Docusaurus-based documentation site. "
143+
144+
if [[ "${{ steps.check-files.outputs.has_important_changes }}" == "true" ]]; then
145+
PROMPT+="IMPORTANT: This PR includes changes to critical configuration files (docusaurus.config.js and/or sidebar files). Please pay special attention to these changes. "
146+
fi
147+
148+
PROMPT+="Please review the changes and check for:
149+
150+
1. **Configuration Integrity**: Ensure docusaurus.config.js changes are valid and won't break the build
151+
2. **Sidebar Structure**: Verify sidebar configurations are properly formatted and all referenced docs exist
152+
3. **Build Impact**: Identify any changes that might affect the documentation build process
153+
4. **Link Validity**: Check that internal links and references are correct
154+
5. **Best Practices**: Ensure changes follow Docusaurus best practices
155+
6. **Performance**: Flag any changes that might impact site performance
156+
157+
Focus primarily on non-markdown files that affect the documentation infrastructure.
158+
159+
Provide specific, actionable feedback with code suggestions where appropriate."
160+
else
161+
# For comments, use the extracted prompt
162+
PROMPT="${{ steps.extract-prompt.outputs.comment_prompt }}"
163+
fi
164+
165+
# Save prompt to file
166+
echo "$PROMPT" > /tmp/review-prompt.txt
167+
echo "Review prompt prepared successfully"
168+
169+
- name: Run Claude Code Review
170+
id: claude-review
171+
uses: anthropics/claude-code-base-action@beta
172+
with:
173+
prompt_file: /tmp/review-prompt.txt
174+
system_prompt: $(cat /tmp/system-prompt.md)
175+
allowed_tools: |
176+
Bash(git:*),
177+
View,
178+
GlobTool,
179+
GrepTool,
180+
Write,
181+
Edit,
182+
Replace,
183+
BatchTool
184+
anthropic_api_key: ${{ secrets.ANTHROPIC_API_KEY }}
185+
timeout_minutes: "15"
186+
max_turns: "10"
187+
model: "claude-4-0-sonnet-20250219"
188+
189+
- name: Generate GitHub App token (for commenting)
190+
id: app-token
191+
if: success() || failure()
192+
uses: actions/create-github-app-token@v2
193+
with:
194+
app-id: ${{ secrets.CLAUDE_APP_ID || vars.CLAUDE_APP_ID }}
195+
private-key: ${{ secrets.CLAUDE_APP_PRIVATE_KEY }}
196+
197+
- name: Post review summary
198+
if: (success() || failure()) && steps.context.outputs.is_pr == 'true'
199+
uses: actions/github-script@v7
200+
with:
201+
github-token: ${{ steps.app-token.outputs.token || secrets.GITHUB_TOKEN }}
202+
script: |
203+
const fs = require('fs');
204+
const executionFile = '${{ steps.claude-review.outputs.execution_file }}';
205+
206+
let reviewContent = '';
207+
let status = '${{ steps.claude-review.outputs.conclusion }}';
208+
209+
if (status === 'success' && fs.existsSync(executionFile)) {
210+
try {
211+
const executionLog = JSON.parse(fs.readFileSync(executionFile, 'utf8'));
212+
213+
// Find the last assistant message which should contain the review
214+
for (let i = executionLog.length - 1; i >= 0; i--) {
215+
if (executionLog[i].role === 'assistant' && executionLog[i].content) {
216+
reviewContent = executionLog[i].content;
217+
break;
218+
}
219+
}
220+
} catch (error) {
221+
console.error('Error parsing execution log:', error);
222+
reviewContent = 'Error: Could not parse Claude\'s response.';
223+
}
224+
} else if (status === 'failure') {
225+
reviewContent = '⚠️ The review could not be completed. Please check the action logs for details.';
226+
}
227+
228+
const summary = `## 🤖 Claude Documentation Review
229+
230+
${reviewContent || 'No review content was generated.'}
231+
232+
---
233+
<sub>Generated by Claude Code Documentation Review Action</sub>`;
234+
235+
await github.rest.issues.createComment({
236+
issue_number: context.issue.number,
237+
owner: context.repo.owner,
238+
repo: context.repo.repo,
239+
body: summary
240+
});
241+
242+
- name: Add workflow summary
243+
if: always()
244+
run: |
245+
echo "## 📊 Claude Review Summary" >> $GITHUB_STEP_SUMMARY
246+
echo "" >> $GITHUB_STEP_SUMMARY
247+
echo "- **Trigger Type**: ${{ steps.context.outputs.trigger_type }}" >> $GITHUB_STEP_SUMMARY
248+
echo "- **Review Status**: ${{ steps.claude-review.outputs.conclusion || 'Not completed' }}" >> $GITHUB_STEP_SUMMARY
249+
echo "- **Important Files Changed**: ${{ steps.check-files.outputs.has_important_changes || 'N/A' }}" >> $GITHUB_STEP_SUMMARY
250+
echo "" >> $GITHUB_STEP_SUMMARY
251+
252+
if [ -f "${{ steps.claude-review.outputs.execution_file }}" ]; then
253+
echo "✅ Review completed. Check the PR comments for Claude's feedback." >> $GITHUB_STEP_SUMMARY
254+
else
255+
echo "❌ Review did not complete successfully." >> $GITHUB_STEP_SUMMARY
256+
fi

0 commit comments

Comments
 (0)