Skip to content

opencode

opencode #22

Workflow file for this run

name: opencode
on:
#schedule:
# - cron: '0 0 * * *'
workflow_dispatch:
inputs:
prompt:
description: 'Custom prompt for the agent (leave empty for daily sync)'
required: false
type: string
issue_comment:
types: [created]
pull_request_review_comment:
types: [created]
pull_request:
types: [opened, synchronize]
# Serialize sync runs, and serialize per-PR comment runs, so concurrent
# dispatches/comments don't race on branch and PR creation.
concurrency:
group: opencode-${{ github.event.issue.number || github.event.pull_request.number || 'sync' }}
cancel-in-progress: false
jobs:
check-upstream:
name: Check Upstream for Updates
if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch'
runs-on: ubuntu-latest
outputs:
has_updates: ${{ steps.check.outputs.has_updates }}
steps:
- name: Checkout repository
uses: actions/checkout@v6
with:
token: ${{ secrets.GITHUB_TOKEN }}
fetch-depth: 0
- name: Check for updates
id: check
run: |
git remote add upstream https://github.com/WildKernels/OnePlus_KernelSU_SUSFS.git
git fetch upstream main
LOCAL_COMMIT=$(git rev-parse HEAD)
UPSTREAM_COMMIT=$(git rev-parse upstream/main)
echo "Local commit: $LOCAL_COMMIT"
echo "Upstream commit: $UPSTREAM_COMMIT"
if ! git merge-base --is-ancestor $UPSTREAM_COMMIT $LOCAL_COMMIT; then
echo "Upstream has new commits."
echo "has_updates=true" >> "$GITHUB_OUTPUT"
else
echo "No new updates from upstream."
echo "has_updates=false" >> "$GITHUB_OUTPUT"
fi
opencode:
name: Run Opencode Agent
needs: [check-upstream]
if: >-
always() && (
(github.event_name == 'schedule' && needs.check-upstream.result == 'success' && needs.check-upstream.outputs.has_updates == 'true') ||
(github.event_name == 'workflow_dispatch') ||
(github.event_name == 'issue_comment' && github.event.comment.user.type != 'Bot' && (contains(github.event.comment.body, ' /oc') || startsWith(github.event.comment.body, '/oc') || contains(github.event.comment.body, ' /opencode') || startsWith(github.event.comment.body, '/opencode'))) ||
(github.event_name == 'pull_request_review_comment' && github.event.comment.user.type != 'Bot' && (contains(github.event.comment.body, ' /oc') || startsWith(github.event.comment.body, '/oc') || contains(github.event.comment.body, ' /opencode') || startsWith(github.event.comment.body, '/opencode')))
)
runs-on: ubuntu-latest
# NOTE: opencode's `opencode github run` emits ~21 lines of internal
# INFO (#NNNN) telemetry/pino logs that CANNOT be suppressed from this
# workflow β€” verified in CI that LOG_LEVEL, OPENCODE_LOG_LEVEL and
# OPENCODE_PRINT_LOGS all have no effect (the lines come from the
# always-on OpenTelemetry logger, not the env-gated stderr printer).
# The agent's own tool/Shell transcript prints to stdout regardless.
# Removing the noise would require forking/wrapping the action.
permissions:
id-token: write
contents: write
pull-requests: write
issues: write
actions: write
steps:
- name: Checkout repository
uses: actions/checkout@v6
with:
token: ${{ secrets.PAT_TOKEN || secrets.GITHUB_TOKEN }}
persist-credentials: true
fetch-depth: 0
- name: Prepare Codebase & Config
shell: bash
env:
OPENAI_BASE_URL: ${{ secrets.OPENAI_BASE_URL }}
OPENAI_MODEL: ${{ secrets.OPENAI_MODEL }}
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
GITHUB_TOKEN: ${{ secrets.PAT_TOKEN || secrets.GITHUB_TOKEN }}
EVENT_NAME: ${{ github.event_name }}
DISPATCH_PROMPT: ${{ github.event.inputs.prompt }}
run: |
echo "::group::Configuring Git"
git config user.name "opencode"
git config user.email "opencode@anomaly.co"
# Ensure git uses the token for pushing
git remote set-url origin https://x-access-token:${GITHUB_TOKEN}@github.com/${{ github.repository }}.git
echo "::endgroup::"
if [[ "$EVENT_NAME" == "schedule" || ( "$EVENT_NAME" == "workflow_dispatch" && ( "$DISPATCH_PROMPT" == "" || "$DISPATCH_PROMPT" == "null" ) ) ]]; then
echo "::group::Automatic Upstream Merge"
git remote add upstream https://github.com/WildKernels/OnePlus_KernelSU_SUSFS.git
git -c http.extraHeader="" fetch --no-tags upstream main
git merge upstream/main --no-edit || echo "Merge conflicts detected (expected)"
echo "::endgroup::"
echo "::group::Auto-resolve merge conflicts (split by ownership)"
# GOAL: take ALL upstream changes AND let THIS workflow commit a real 2-parent
# merge commit (so the sync PR contains the upstream commits + a merge commit
# and merge-base advances). Every conflict is resolved deterministically below
# -- nothing is left for the agent -- because the agent's tool flattens its
# commit to a single parent and would drop the upstream ancestry.
#
# Non-conflicting upstream edits -- including ones under .github/** -- are
# ALREADY merged in by `git merge` above, so upstream CI improvements (SusFS
# support, cache fixes, ...) in areas the fork didn't touch flow in for free.
#
# Only directly CONFLICTING hunks are resolved here, split by ownership:
# * Fork-owned CI/docs (.github/**, README, ...) keep OURS -- the fork is a
# heavy rewrite (ReSukiSU branding, ccache job, model-link table, DWC3, KSUN
# removal, t.me links); a blind --theirs would drop those.
# * Everything else (device configs, manifests, kernel sources) takes
# UPSTREAM; sanitize.py below re-applies the deterministic fork transforms
# (uname -> OP-RESUKISU, AnyKernel3 URL, ...).
git ls-files -u 2>/dev/null | awk '{print $4}' | sort -u | while IFS= read -r f; do
[ -z "$f" ] && continue
case "$f" in
.github/*|README.md|compatibility.md|LICENSE)
# Fork-owned CI/docs: for directly COLLIDING hunks keep OURS so fork CI
# stays working. Non-conflicting upstream edits to these files were
# ALREADY merged cleanly by `git merge` above, so upstream CI improvements
# in areas the fork didn't touch still flow in -- only hunks that overlap
# a fork customization fall back to fork.
#
# Resolving HERE (rather than leaving the conflict for the opencode agent)
# is deliberate: it lets THIS workflow commit a real 2-parent merge commit
# below. The agent runs in a tool that flattens its commit to a single
# parent, which drops the upstream ancestry -- main's merge-base would
# never advance and every sync would re-merge the same commits. Keeping
# the merge in the workflow makes the sync PR contain the upstream commits
# + one merge commit, and advances merge-base.
git checkout --ours -- "$f" 2>/dev/null || true
git add -- "$f" 2>/dev/null || true
;;
*)
# Device configs, manifests, kernel sources: take UPSTREAM; sanitize.py
# below re-applies deterministic fork transforms (uname, URLs).
git checkout --theirs -- "$f" 2>/dev/null || git rm -f --quiet "$f" 2>/dev/null || true
git add -- "$f" 2>/dev/null || true
;;
esac
done
echo "Remaining unmerged after auto-resolve: $(git ls-files -u 2>/dev/null | awk '{print $4}' | sort -u | wc -l | tr -d ' ')"
echo "::endgroup::"
fi
echo "::group::Sanitize & Ignore Rules"
# Count distinct conflicted files (git ls-files -u lists 3 stage rows per file).
CONFLICT_COUNT=$(git ls-files -u 2>/dev/null | awk '{print $4}' | sort -u | wc -l | tr -d ' ')
python3 .github/opencode/sanitize.py
if [ "$CONFLICT_COUNT" -eq 0 ]; then
git add -A
git commit -m "chore: merge upstream/main + sanitize" || echo "No changes to commit"
else
# Write conflict scratch files OUTSIDE the work tree so the agent's
# `git add -A` never commits them into the repo. Read back via $RUNNER_TEMP.
git ls-files -u 2>/dev/null | awk '{print $4}' | sort -u > "$RUNNER_TEMP/conflict_files.txt"
{
echo "The following files have UNRESOLVED MERGE CONFLICTS. Conflict markers are at these exact lines:"
echo ""
while IFS= read -r f; do
[ -z "$f" ] && continue
echo "=== $f ==="
grep -n '<<<<<<< HEAD\|=======\|>>>>>>> upstream/main' "$f" 2>/dev/null || echo " (markers not found in working copy, check git diff)"
echo ""
done < "$RUNNER_TEMP/conflict_files.txt"
} > "$RUNNER_TEMP/conflict_summary.txt"
echo "Merge has $CONFLICT_COUNT conflict file(s), skipping commit. Conflict summary saved."
fi
echo "::endgroup::"
echo "::group::Preparing opencode.json"
# Ensure defaults to prevent invalid JSON if secrets are missing
echo "OPENAI_BASE_URL=${OPENAI_BASE_URL:-https://api.openai.com/v1}" >> "$GITHUB_ENV"
echo "OPENAI_MODEL=${OPENAI_MODEL:-gpt-4o}" >> "$GITHUB_ENV"
# We need to source them for the current step too
export OPENAI_BASE_URL="${OPENAI_BASE_URL:-https://api.openai.com/v1}"
export OPENAI_MODEL="${OPENAI_MODEL:-gpt-4o}"
# Create opencode.json from template, substituting environment variables
envsubst < .github/opencode/opencode.json > opencode.json
echo "::endgroup::"
- name: Auto-PR on Clean Merge
id: merge-check
if: always() && (github.event_name == 'schedule' || (github.event_name == 'workflow_dispatch' && (github.event.inputs.prompt == '' || github.event.inputs.prompt == 'null')))
env:
GH_TOKEN: ${{ secrets.PAT_TOKEN || secrets.GITHUB_TOKEN }}
TG_BOT_TOKEN: ${{ secrets.TG_BOT_TOKEN }}
TG_CHAT_ID: ${{ secrets.TG_TEST_CHAT_ID || secrets.TG_CHAT_ID }}
run: |
CONFLICTS=$(git ls-files -u 2>/dev/null | awk '{print $4}' | sort -u | wc -l | tr -d ' ')
if [ "$CONFLICTS" -gt 0 ]; then
echo "has_conflicts=true" >> "$GITHUB_OUTPUT"
echo "Merge has $CONFLICTS conflict file(s), agent will resolve."
exit 0
fi
echo "has_conflicts=false" >> "$GITHUB_OUTPUT"
AHEAD=$(git rev-list --count origin/main..HEAD)
echo "Commits ahead of origin/main: $AHEAD"
if [ "$AHEAD" -eq 0 ]; then
echo "skip_agent=true" >> "$GITHUB_OUTPUT"
echo "No new commits, nothing to do."
exit 0
fi
# Reuse an already-open upstream-sync PR instead of spawning a duplicate.
# Only matches bot-managed `opencode/upstream-sync-*` branches (never the
# agent's `dispatch-*` conflict branches, so no agent work is clobbered).
EXISTING=$(gh pr list --repo "${{ github.repository }}" --state open --base main \
--json number,headRefName \
--jq '[.[] | select(.headRefName | startswith("opencode/upstream-sync-"))][0] // {}')
EXISTING_BRANCH=$(echo "$EXISTING" | jq -r '.headRefName // empty')
EXISTING_NUM=$(echo "$EXISTING" | jq -r '.number // empty')
if [ -n "$EXISTING_BRANCH" ]; then
BRANCH="$EXISTING_BRANCH"
# Bot-only branch: force-update it to the freshly merged state.
git push origin "HEAD:refs/heads/$BRANCH" --force
PR_URL=$(gh pr view "$EXISTING_NUM" --repo "${{ github.repository }}" --json url --jq '.url')
gh pr comment "$EXISTING_NUM" --repo "${{ github.repository }}" \
--body "♻️ Refreshed with latest upstream ($AHEAD commits ahead of main)."
echo "Reused existing sync PR #$EXISTING_NUM ($BRANCH)."
else
BRANCH="opencode/upstream-sync-$(date +%Y%m%d%H%M%S)"
git checkout -b "$BRANCH"
git push origin "$BRANCH"
sleep 10
PR_URL=$(gh pr create \
--title "πŸ”„ Sync upstream $(date +%Y-%m-%d)" \
--body "Automatic upstream sync. No conflicts detected." \
--base main \
--head "$BRANCH" \
--repo "${{ github.repository }}")
echo "PR created: $PR_URL"
fi
echo "skip_agent=true" >> "$GITHUB_OUTPUT"
if [ -n "$TG_BOT_TOKEN" ] && [ -n "$TG_CHAT_ID" ]; then
MSG="βœ… <b>Upstream Sync PR Created</b>"$'\n'
MSG+="━━━━━━━━━━━━━━━━━━"$'\n'
MSG+="<b>PR:</b> <a href=\"$PR_URL\">$PR_URL</a>"$'\n'
MSG+="<b>Ahead by:</b> $AHEAD commits"
IFS=' ,' read -r -a CHAT_IDS <<< "$TG_CHAT_ID"
for ID in "${CHAT_IDS[@]}"; do
[ -z "$ID" ] && continue
PAYLOAD=$(jq -n --arg chat_id "$ID" --arg text "$MSG" '{chat_id: $chat_id, parse_mode: "HTML", disable_web_page_preview: true, text: $text}')
curl -s -X POST "https://api.telegram.org/bot${TG_BOT_TOKEN}/sendMessage" -H "Content-Type: application/json" -d "$PAYLOAD" > /dev/null
done
fi
- name: Prepare Prompt
id: prep
env:
GH_TOKEN: ${{ secrets.PAT_TOKEN || secrets.GITHUB_TOKEN }}
COMMENT_BODY: ${{ github.event.comment.body }}
EVENT_NAME: ${{ github.event_name }}
DISPATCH_PROMPT: ${{ github.event.inputs.prompt }}
run: |
TASK_DESC="Synchronizing upstream and resolving conflicts."
if [[ "$EVENT_NAME" == "schedule" || ( "$EVENT_NAME" == "workflow_dispatch" && ( "$DISPATCH_PROMPT" == "" || "$DISPATCH_PROMPT" == "null" ) ) ]]; then
{
echo "A 'git merge upstream/main' has already been attempted. Automatic scripts have also fixed AnyKernel3 URLs, 'uname' fields, and KSUN removal."
echo "Your primary task is to:"
echo "1. Resolve any UNRESOLVED CONFLICTS."
echo "2. Final audit against guidelines."
echo ""
if [ -f "$RUNNER_TEMP/conflict_summary.txt" ]; then
echo "========== CONFLICT DETAILS =========="
cat "$RUNNER_TEMP/conflict_summary.txt"
echo "====================================="
echo ""
fi
cat .github/opencode/guidelines.txt
} > final_prompt.txt
elif [[ "$EVENT_NAME" == "issue_comment" || "$EVENT_NAME" == "pull_request_review_comment" ]]; then
TASK_DESC="Processing user request from comment."
PR_OR_ISSUE_NUMBER="${{ github.event.issue.number || github.event.pull_request.number }}"
echo "Fetching comment history for #$PR_OR_ISSUE_NUMBER..."
gh api repos/${{ github.repository }}/issues/$PR_OR_ISSUE_NUMBER/comments | jq -r '.[].body' > user_comment.txt
TRIMMED_COMMENT=$(echo "$COMMENT_BODY" | xargs)
EXTRA_INSTRUCTION=""
if [[ "$TRIMMED_COMMENT" == "/oc" || "$TRIMMED_COMMENT" == "/opencode" ]]; then
EXTRA_INSTRUCTION="The user triggered the agent with an empty '/oc' command. This is a shorthand request. Please implicitly execute the following: \"please review the build logs, fetch the corresponding kernel source code and other .patch files if needed, and fix the compile errors\""
fi
{
echo "Interactive mode. The user requested the following in a PR/Issue comment thread:";
echo "-----------------";
cat user_comment.txt;
echo "-----------------";
if [[ -n "$EXTRA_INSTRUCTION" ]]; then
echo "";
echo "$EXTRA_INSTRUCTION";
fi
echo "";
echo "Please fulfill the user's request while strictly adhering to these guidelines:";
echo "";
cat .github/opencode/guidelines.txt;
} > final_prompt.txt
rm -f user_comment.txt
elif [[ "$EVENT_NAME" == "workflow_dispatch" && "$DISPATCH_PROMPT" != "" ]]; then
TASK_DESC="Processing manual workflow dispatch prompt."
{ printf '%s\n' "$DISPATCH_PROMPT"; echo ""; echo "---"; cat .github/opencode/guidelines.txt; } > final_prompt.txt
else
echo "" > final_prompt.txt
fi
# Random delimiter so a line equal to "EOF" inside the prompt can't break the output.
DELIM="EOF_$(openssl rand -hex 8)"
{ echo "prompt<<$DELIM"; cat final_prompt.txt; echo "$DELIM"; } >> "$GITHUB_OUTPUT"
echo "task_desc=$TASK_DESC" >> "$GITHUB_OUTPUT"
rm -f final_prompt.txt
- name: Notify TG (Agent Start)
if: always()
continue-on-error: true
env:
TG_BOT_TOKEN: ${{ secrets.TG_BOT_TOKEN }}
TG_CHAT_ID: ${{ secrets.TG_TEST_CHAT_ID || secrets.TG_CHAT_ID }}
run: |
if [ -z "$TG_BOT_TOKEN" ] || [ -z "$TG_CHAT_ID" ]; then exit 0; fi
TASK="${{ steps.prep.outputs.task_desc }}"
[ -z "$TASK" ] && TASK="Unknown task"
MSG="πŸš€ <b>Opencode Agent is Starting</b>"$'\n'
MSG+="━━━━━━━━━━━━━━━━━━"$'\n'
MSG+="<b>Task:</b> $TASK"
IFS=' ,' read -r -a CHAT_IDS <<< "$TG_CHAT_ID"
for ID in "${CHAT_IDS[@]}"; do
[ -z "$ID" ] && continue
PAYLOAD=$(jq -n --arg chat_id "$ID" --arg text "$MSG" '{chat_id: $chat_id, parse_mode: "HTML", disable_web_page_preview: true, text: $text}')
curl -s -X POST "https://api.telegram.org/bot${TG_BOT_TOKEN}/sendMessage" -H "Content-Type: application/json" -d "$PAYLOAD" > /dev/null
done
- name: Run opencode
id: agent
if: steps.merge-check.outputs.skip_agent != 'true'
uses: anomalyco/opencode/github@latest
env:
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
OPENAI_BASE_URL: ${{ env.OPENAI_BASE_URL }}
OPENAI_MODEL: ${{ env.OPENAI_MODEL }}
GITHUB_TOKEN: ${{ secrets.PAT_TOKEN || secrets.GITHUB_TOKEN }}
GH_TOKEN: ${{ secrets.PAT_TOKEN || secrets.GITHUB_TOKEN }}
with:
model: custom-openai/${{ env.OPENAI_MODEL }}
prompt: ${{ steps.prep.outputs.prompt }}
use_github_token: true
- name: Cleanup Custom Provider Config
if: always()
run: rm -f opencode.json
- name: Notify TG (Agent Finish)
if: always()
continue-on-error: true
env:
TG_BOT_TOKEN: ${{ secrets.TG_BOT_TOKEN }}
TG_CHAT_ID: ${{ secrets.TG_TEST_CHAT_ID || secrets.TG_CHAT_ID }}
run: |
if [ -z "$TG_BOT_TOKEN" ] || [ -z "$TG_CHAT_ID" ]; then exit 0; fi
STATUS="${{ steps.agent.outcome }}"; EMOJI="βœ…"; [ "$STATUS" != "success" ] && EMOJI="❌"
MSG="${EMOJI} <b>Opencode Agent Finished</b>"$'\n'
MSG+="━━━━━━━━━━━━━━━━━━"$'\n'
MSG+="<b>Result:</b> <code>${STATUS}</code>"$'\n'
MSG+="<b>Note:</b> A new Pull Request should be available soon."
IFS=' ,' read -r -a CHAT_IDS <<< "$TG_CHAT_ID"
for ID in "${CHAT_IDS[@]}"; do
[ -z "$ID" ] && continue
PAYLOAD=$(jq -n --arg chat_id "$ID" --arg text "$MSG" '{chat_id: $chat_id, parse_mode: "HTML", disable_web_page_preview: true, text: $text}')
curl -s -X POST "https://api.telegram.org/bot${TG_BOT_TOKEN}/sendMessage" -H "Content-Type: application/json" -d "$PAYLOAD" > /dev/null
done
# -------- PULL REQUEST WORKFLOW CHAIN --------
auto-mirror:
name: Auto-Mirror Toolchains
if: github.event_name == 'pull_request' && startsWith(github.event.pull_request.head.ref, 'opencode/')
runs-on: ubuntu-latest
permissions:
actions: write
contents: read
pull-requests: read
steps:
- name: Checkout Code
uses: actions/checkout@v6
with:
token: ${{ secrets.GITHUB_TOKEN }}
fetch-depth: 0
- name: Check for Changes & Trigger
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
git fetch origin ${{ github.event.pull_request.base.ref }}
if git diff --name-only origin/${{ github.event.pull_request.base.ref }} HEAD | grep -E 'manifests/|configs/'; then
echo "Toolchain changes detected."
PR_BRANCH="${{ github.event.pull_request.head.ref }}"
gh workflow run mirror-toolchains.yml --repo ${{ github.repository }} --ref "$PR_BRANCH"
# Poll for the run we just dispatched on THIS branch (avoid grabbing another branch's run).
RUN_ID=""
for _ in $(seq 1 12); do
sleep 5
RUN_ID=$(gh run list --workflow=mirror-toolchains.yml --branch "$PR_BRANCH" --event workflow_dispatch --limit 1 --json databaseId -q '.[0].databaseId' --repo ${{ github.repository }})
[ -n "$RUN_ID" ] && break
done
if [ -n "$RUN_ID" ]; then
gh run watch $RUN_ID --repo ${{ github.repository }} --exit-status || echo "Mirroring failed, proceeding anyway..."
fi
else
echo "No toolchain changes."
fi
trigger-test-build:
name: Trigger Test Build
needs: [auto-mirror]
# always(): still run the build even if auto-mirror failed/was skipped.
if: always() && github.event_name == 'pull_request' && startsWith(github.event.pull_request.head.ref, 'opencode/')
runs-on: ubuntu-latest
permissions:
actions: write
contents: read
steps:
- name: Trigger build-kernel-release.yml
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
PR_BRANCH="${{ github.event.pull_request.head.ref }}"
gh workflow run build-kernel-release.yml --repo ${{ github.repository }} --ref "$PR_BRANCH" -f make_release=false
# Poll for the run we just dispatched on THIS branch (avoid grabbing another branch's run).
RUN_ID=""
for _ in $(seq 1 12); do
sleep 5
RUN_ID=$(gh run list --workflow=build-kernel-release.yml --branch "$PR_BRANCH" --event workflow_dispatch --limit 1 --json databaseId -q '.[0].databaseId' --repo ${{ github.repository }})
[ -n "$RUN_ID" ] && break
done
if [ -n "$RUN_ID" ]; then
gh run watch $RUN_ID --repo ${{ github.repository }} --exit-status
else
exit 1
fi
report-test-result:
name: Report and Auto-Fix
needs: [trigger-test-build]
if: always() && github.event_name == 'pull_request' && startsWith(github.event.pull_request.head.ref, 'opencode/')
runs-on: ubuntu-latest
permissions:
id-token: write
contents: write
pull-requests: write
issues: write
actions: write
steps:
- name: Checkout repository
uses: actions/checkout@v6
with:
token: ${{ secrets.GITHUB_TOKEN }}
- name: Prepare & Send TG Message
env:
TG_BOT_TOKEN: ${{ secrets.TG_BOT_TOKEN }}
TG_CHAT_ID: ${{ secrets.TG_TEST_CHAT_ID || secrets.TG_CHAT_ID }}
run: |
STATUS="${{ needs.trigger-test-build.result }}"; EMOJI="βœ…"; [ "$STATUS" != "success" ] && EMOJI="❌"
MSG_TEXT="${EMOJI} <b>Opencode PR Test Build Finished</b>"$'\n'
MSG_TEXT+="━━━━━━━━━━━━━━━━━━"$'\n'
MSG_TEXT+="<b>Result:</b> <code>${STATUS}</code>"$'\n'
MSG_TEXT+="<b>PR:</b> <a href=\"${{ github.event.pull_request.html_url }}\">#${{ github.event.pull_request.number }}</a>"$'\n'
if [ "$STATUS" != "success" ]; then
MSG_TEXT+="━━━━━━━━━━━━━━━━━━"$'\n'
MSG_TEXT+="πŸ‘‰ <i>The build failed. To ask the agent to fix it, comment:</i>"$'\n'
MSG_TEXT+="<code>/oc please review the build logs, fetch the corresponding kernel source code and other .patch files if needed, and fix the compile errors</code>"
fi
PAYLOAD=$(jq -n --arg chat_id "$TG_CHAT_ID" --arg text "$MSG_TEXT" '{chat_id: $chat_id, parse_mode: "HTML", disable_web_page_preview: true, text: $text}')
curl -s -X POST "https://api.telegram.org/bot${TG_BOT_TOKEN}/sendMessage" -H "Content-Type: application/json" -d "$PAYLOAD" > /dev/null
- name: Auto-Comment on PR
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
STATUS="${{ needs.trigger-test-build.result }}"
PR_NUMBER="${{ github.event.pull_request.number }}"
if [ "$STATUS" == "success" ]; then
COMMENT="βœ… **Test build passed successfully!** πŸŽ‰"
else
COMMENT=$(cat << 'EOF'
❌ **Test build failed.**
The AI agent can attempt to fix the errors. Please check the action logs, and reply to this PR with:
`/oc please review the build logs, fetch the corresponding kernel source code and other .patch files if needed, and fix the compile errors`
EOF
)
fi
gh pr comment $PR_NUMBER --body "$COMMENT" --repo "${{ github.repository }}"
- name: Fail the workflow
if: needs.trigger-test-build.result != 'success'
run: exit 1