Skip to content

Commit a6552b1

Browse files
Merge branch 'main' into add-qwen-chatbot-agent
2 parents 923cbd1 + a3a9989 commit a6552b1

31 files changed

+9173
-43
lines changed
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
FROM node:20-alpine
2+
3+
RUN npm install -g @anthropic-ai/claude-code
4+
5+
WORKDIR /app
6+
COPY entrypoint.sh .
7+
RUN chmod +x entrypoint.sh
8+
9+
ENTRYPOINT ["/app/entrypoint.sh"]
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
name: "Claude Code Action"
2+
description: "Custom Claude Code runner for PraisonAI"
3+
4+
inputs:
5+
anthropic_api_key:
6+
required: true
7+
description: "Anthropic API key"
8+
github_token:
9+
required: true
10+
description: "GitHub token for repo access"
11+
12+
runs:
13+
using: "docker"
14+
image: "docker://ghcr.io/mervinpraison/praisonai-claudecode:latest"
15+
env:
16+
ANTHROPIC_API_KEY: ${{ inputs.anthropic_api_key }}
17+
GITHUB_TOKEN: ${{ inputs.github_token }}
18+
args:
19+
- "--anthropic-api-key=${{ inputs.anthropic_api_key }}"
20+
- "--github-token=${{ inputs.github_token }}"
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
#!/bin/sh
2+
3+
set -e
4+
5+
echo "Running Claude Code in CI mode..."
6+
7+
# Debug environment
8+
echo "Current PATH: $PATH"
9+
echo "Available commands:"
10+
which node || echo "node not found"
11+
which npm || echo "npm not found"
12+
which claude || echo "claude not found"
13+
14+
# Check if claude is installed
15+
if ! command -v claude >/dev/null 2>&1; then
16+
echo "Error: claude command not found"
17+
echo "Attempting to install claude..."
18+
npm install -g @anthropic-ai/claude-code || {
19+
echo "Failed to install claude"
20+
exit 1
21+
}
22+
fi
23+
24+
# Extract GitHub context and create a smart prompt
25+
PROMPT="Analyse the GitHub issue or PR context and generate a smart response based on the repository context."
26+
27+
# Set environment variables from arguments
28+
export ANTHROPIC_API_KEY="${1#--anthropic-api-key=}"
29+
export GITHUB_TOKEN="${2#--github-token=}"
30+
31+
# Debug environment variables
32+
echo "ANTHROPIC_API_KEY set: $([ -n "$ANTHROPIC_API_KEY" ] && echo "yes" || echo "no")"
33+
echo "GITHUB_TOKEN set: $([ -n "$GITHUB_TOKEN" ] && echo "yes" || echo "no")"
34+
35+
# Verify environment variables
36+
if [ -z "$ANTHROPIC_API_KEY" ] || [ -z "$GITHUB_TOKEN" ]; then
37+
echo "Error: Required environment variables are not set"
38+
echo "Args received: $@"
39+
exit 1
40+
fi
41+
42+
# Find the actual claude script and run it with node directly to bypass BusyBox env issues
43+
echo "Finding claude script..."
44+
CLAUDE_SCRIPT=$(which claude)
45+
echo "Claude script location: $CLAUDE_SCRIPT"
46+
47+
# Run Claude directly with node to avoid BusyBox env -S issue
48+
echo "Running claude command with node..."
49+
exec node "$CLAUDE_SCRIPT" -p "$PROMPT"
Lines changed: 117 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
name: "Claude Code Action"
2+
description: "Run Claude Code in GitHub Actions workflows"
3+
4+
inputs:
5+
github_token:
6+
description: "GitHub token with repo and issues permissions"
7+
required: true
8+
anthropic_api_key:
9+
description: "Anthropic API key"
10+
required: true
11+
prompt:
12+
description: "The prompt to send to Claude Code"
13+
required: false
14+
default: ""
15+
prompt_file:
16+
description: "Path to a file containing the prompt to send to Claude Code"
17+
required: false
18+
default: ""
19+
allowed_tools:
20+
description: "Comma-separated list of allowed tools for Claude Code to use"
21+
required: false
22+
default: ""
23+
output_file:
24+
description: "File to save Claude Code output to (optional)"
25+
required: false
26+
default: ""
27+
timeout_minutes:
28+
description: "Timeout in minutes for Claude Code execution"
29+
required: false
30+
default: "10"
31+
install_github_mcp:
32+
description: "Whether to install the GitHub MCP server"
33+
required: false
34+
default: "false"
35+
36+
runs:
37+
using: "composite"
38+
steps:
39+
- name: Install Claude Code
40+
shell: bash
41+
run: npm install -g @anthropic-ai/claude-code
42+
43+
- name: Install GitHub MCP Server
44+
if: inputs.install_github_mcp == 'true'
45+
shell: bash
46+
run: |
47+
claude mcp add-json github '{
48+
"command": "docker",
49+
"args": [
50+
"run",
51+
"-i",
52+
"--rm",
53+
"-e",
54+
"GITHUB_PERSONAL_ACCESS_TOKEN",
55+
"ghcr.io/github/github-mcp-server:sha-ff3036d"
56+
],
57+
"env": {
58+
"GITHUB_PERSONAL_ACCESS_TOKEN": "${{ inputs.GITHUB_TOKEN }}"
59+
}
60+
}'
61+
62+
- name: Prepare Prompt File
63+
shell: bash
64+
id: prepare_prompt
65+
run: |
66+
if [ -z "${{ inputs.prompt }}" ] && [ -z "${{ inputs.prompt_file }}" ]; then
67+
echo "::error::Neither 'prompt' nor 'prompt_file' was provided. At least one is required."
68+
exit 1
69+
fi
70+
71+
if [ ! -z "${{ inputs.prompt_file }}" ]; then
72+
if [ ! -f "${{ inputs.prompt_file }}" ]; then
73+
echo "::error::Prompt file '${{ inputs.prompt_file }}' does not exist."
74+
exit 1
75+
fi
76+
PROMPT_PATH="${{ inputs.prompt_file }}"
77+
else
78+
mkdir -p /tmp/claude-action
79+
PROMPT_PATH="/tmp/claude-action/prompt.txt"
80+
echo "${{ inputs.prompt }}" > "$PROMPT_PATH"
81+
fi
82+
83+
if [ ! -s "$PROMPT_PATH" ]; then
84+
echo "::error::Prompt is empty. Please provide a non-empty prompt."
85+
exit 1
86+
fi
87+
88+
echo "PROMPT_PATH=$PROMPT_PATH" >> $GITHUB_ENV
89+
90+
- name: Run Claude Code
91+
shell: bash
92+
id: run_claude
93+
run: |
94+
timeout_seconds=$((${{ inputs.timeout_minutes }} * 60))
95+
96+
if [ -z "${{ inputs.output_file }}" ]; then
97+
timeout $timeout_seconds claude \
98+
-p \
99+
--verbose \
100+
--output-format stream-json \
101+
"$(cat ${{ env.PROMPT_PATH }})" \
102+
${{ inputs.allowed_tools != '' && format('--allowedTools "{0}"', inputs.allowed_tools) || '' }}
103+
else
104+
timeout $timeout_seconds claude \
105+
-p \
106+
--verbose \
107+
--output-format stream-json \
108+
"$(cat ${{ env.PROMPT_PATH }})" \
109+
${{ inputs.allowed_tools != '' && format('--allowedTools "{0}"', inputs.allowed_tools) || '' }} | tee output.txt
110+
111+
jq -s '.' output.txt > output.json
112+
jq -r '.[-1].result' output.json > "${{ inputs.output_file }}"
113+
echo "Complete output saved to output.json, final response saved to ${{ inputs.output_file }}"
114+
fi
115+
env:
116+
ANTHROPIC_API_KEY: ${{ inputs.anthropic_api_key }}
117+
GITHUB_TOKEN: ${{ inputs.github_token }}

.github/workflows/build-image.yml

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
name: Build Claude Code Image
2+
3+
on:
4+
workflow_dispatch:
5+
inputs:
6+
version:
7+
description: 'Image version tag'
8+
required: true
9+
default: 'latest'
10+
11+
jobs:
12+
build:
13+
runs-on: ubuntu-latest
14+
permissions:
15+
contents: read
16+
packages: write
17+
steps:
18+
- name: Checkout repository
19+
uses: actions/checkout@v4
20+
21+
- name: Set up Docker Buildx
22+
uses: docker/setup-buildx-action@v3
23+
24+
- name: Login to GitHub Container Registry
25+
uses: docker/login-action@v3
26+
with:
27+
registry: ghcr.io
28+
username: ${{ github.actor }}
29+
password: ${{ secrets.GH_TOKEN }}
30+
31+
- name: Build and push Docker image
32+
uses: docker/build-push-action@v5
33+
with:
34+
context: ./.github/actions/claude-code-action
35+
push: true
36+
platforms: linux/amd64
37+
tags: ghcr.io/mervinpraison/praisonai-claudecode:${{ inputs.version }}
38+
cache-from: type=gha
39+
cache-to: type=gha,mode=max
40+
provenance: false

.github/workflows/claude.yml

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,15 +23,24 @@ jobs:
2323
pull-requests: read
2424
issues: read
2525
id-token: write
26+
packages: read
2627
steps:
2728
- name: Checkout repository
2829
uses: actions/checkout@v4
2930
with:
3031
fetch-depth: 1
3132

33+
- name: Fix GHCR Authentication Bug
34+
run: |
35+
echo "=== Applying GHCR workaround ==="
36+
docker logout ghcr.io || true
37+
echo "${{ secrets.GH_TOKEN }}" | docker login ghcr.io -u MervinPraison --password-stdin
38+
docker pull ghcr.io/mervinpraison/praisonai-claudecode:latest
39+
3240
- name: Run Claude Code
3341
id: claude
34-
uses: anthropics/claude-code-action@beta
42+
uses: ./.github/actions/claude-code-action
3543
with:
3644
anthropic_api_key: ${{ secrets.ANTHROPIC_API_KEY }}
45+
github_token: ${{ secrets.GH_TOKEN }}
3746

docker/Dockerfile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ RUN mkdir -p /root/.praison
1616
# Install Python packages (using latest versions)
1717
RUN pip install --no-cache-dir \
1818
flask \
19-
"praisonai>=2.2.31" \
19+
"praisonai>=2.2.33" \
2020
"praisonai[api]" \
2121
gunicorn \
2222
markdown

docker/Dockerfile.chat

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ RUN mkdir -p /root/.praison
1616
# Install Python packages (using latest versions)
1717
RUN pip install --no-cache-dir \
1818
praisonai_tools \
19-
"praisonai>=2.2.31" \
19+
"praisonai>=2.2.33" \
2020
"praisonai[chat]" \
2121
"embedchain[github,youtube]"
2222

docker/Dockerfile.dev

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ RUN mkdir -p /root/.praison
2020
# Install Python packages (using latest versions)
2121
RUN pip install --no-cache-dir \
2222
praisonai_tools \
23-
"praisonai>=2.2.31" \
23+
"praisonai>=2.2.33" \
2424
"praisonai[ui]" \
2525
"praisonai[chat]" \
2626
"praisonai[realtime]" \

docker/Dockerfile.ui

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ RUN mkdir -p /root/.praison
1616
# Install Python packages (using latest versions)
1717
RUN pip install --no-cache-dir \
1818
praisonai_tools \
19-
"praisonai>=2.2.31" \
19+
"praisonai>=2.2.33" \
2020
"praisonai[ui]" \
2121
"praisonai[crewai]"
2222

0 commit comments

Comments
 (0)