Refactor auto-release workflow for clarity and reliability

Renamed workflow, improved job and step naming, and streamlined artifact zipping and release note generation. Switched to using softprops/action-gh-release for release creation and asset upload, removed manual commit list preparation, and enhanced error handling for release note generation. Updated permissions and environment variables for consistency.
This commit is contained in:
手瓜一十雪 2025-11-13 18:46:48 +08:00
parent 0181700c3b
commit 4abd0668a3

View File

@ -1,26 +1,28 @@
name: Build Release (OpenRouter AI notes on tag) name: "Build Action"
on: on:
workflow_dispatch:
push: push:
branches:
- main
tags: tags:
- '*' # 任意 tag push 时触发,可改为 'v*.*.*' - '*' # 任意 tag push 时触发
permissions: permissions: write-all
contents: write
env: env:
OPENROUTER_API_URL: https://openrouter.ai/api/v1/chat/completions OPENROUTER_API_URL: https://openrouter.ai/api/v1/chat/completions
OPENROUTER_MODEL: "deepseek/deepseek-chat-v3-0324:free" OPENROUTER_MODEL: "openrouter/auto"
RELEASE_NAME: "NapCat" RELEASE_NAME: "NapCat"
jobs: jobs:
Build-LiteLoader: Build-LiteLoader:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v4 - name: Clone Main Repository
with: uses: actions/checkout@v4
fetch-depth: 0 - name: Use Node.js 20.X
- uses: actions/setup-node@v4 uses: actions/setup-node@v4
with: with:
node-version: 20.x node-version: 20.x
- name: Build NapCat.Framework - name: Build NapCat.Framework
@ -32,7 +34,7 @@ jobs:
mv packages/napcat-framework/dist framework-dist mv packages/napcat-framework/dist framework-dist
cd framework-dist cd framework-dist
npm install --omit=dev npm install --omit=dev
rm -f package-lock.json rm ./package-lock.json || exit 0
- name: Upload Artifact - name: Upload Artifact
uses: actions/upload-artifact@v4 uses: actions/upload-artifact@v4
with: with:
@ -42,10 +44,10 @@ jobs:
Build-Shell: Build-Shell:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v4 - name: Clone Main Repository
with: uses: actions/checkout@v4
fetch-depth: 0 - name: Use Node.js 20.X
- uses: actions/setup-node@v4 uses: actions/setup-node@v4
with: with:
node-version: 20.x node-version: 20.x
- name: Build NapCat.Shell - name: Build NapCat.Shell
@ -57,7 +59,7 @@ jobs:
mv packages/napcat-shell/dist shell-dist mv packages/napcat-shell/dist shell-dist
cd shell-dist cd shell-dist
npm install --omit=dev npm install --omit=dev
rm -f package-lock.json rm ./package-lock.json || exit 0
- name: Upload Artifact - name: Upload Artifact
uses: actions/upload-artifact@v4 uses: actions/upload-artifact@v4
with: with:
@ -68,35 +70,20 @@ jobs:
needs: [Build-LiteLoader, Build-Shell] needs: [Build-LiteLoader, Build-Shell]
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v4 - name: Checkout
with: uses: actions/checkout@v4
fetch-depth: 0
- name: Download artifacts - name: Download Artifacts
uses: actions/download-artifact@v4 uses: actions/download-artifact@v4
with: with:
path: ./artifacts path: ./artifacts
- name: Make zips - name: Zip Artifacts
run: | run: |
cd artifacts || exit 0 cd artifacts
[ -d NapCat.Shell ] && (cd NapCat.Shell && zip -qr ../NapCat.Shell.zip .) [ -d NapCat.Framework ] && zip -qr ../NapCat.Framework.zip -r NapCat.Framework
[ -d NapCat.Framework ] && (cd NapCat.Framework && zip -qr ../NapCat.Framework.zip .) [ -d NapCat.Shell ] && zip -qr ../NapCat.Shell.zip -r NapCat.Shell
cd .. cd ..
ls -la
- name: Prepare commits list
run: |
TAG="${GITHUB_REF#refs/tags/}"
git fetch --all --tags || true
PREV_TAG=$(git tag --sort=-creatordate | grep -v "^$" | awk -v t="$TAG" '$0!=t{print; exit}')
if [ -n "$PREV_TAG" ]; then
git log --pretty=format:'%h %s (%an)' "$PREV_TAG..$TAG" > /tmp/commits.txt || git log --pretty=format:'%h %s (%an)' -n 30 > /tmp/commits.txt
else
git log --pretty=format:'%h %s (%an)' -n 30 > /tmp/commits.txt
fi
echo "=== commits ==="
sed -n '1,200p' /tmp/commits.txt || true
- name: Generate release note via OpenRouter - name: Generate release note via OpenRouter
env: env:
@ -105,12 +92,11 @@ jobs:
OPENROUTER_MODEL: ${{ env.OPENROUTER_MODEL }} OPENROUTER_MODEL: ${{ env.OPENROUTER_MODEL }}
run: | run: |
set -euo pipefail set -euo pipefail
PROMPT_FILE=".github/prompt/release_note_prompt.txt"
TAG="${GITHUB_REF#refs/tags/}" TAG="${GITHUB_REF#refs/tags/}"
ARTIFACTS_LIST=$(ls ./artifacts 2>/dev/null | tr '\n' ',' | sed 's/,$//') COMMITS=$(git log --pretty=format:'%h %s (%an)' -n 30)
COMMITS=$(sed 's/"/\\"/g' /tmp/commits.txt || echo "无提交信息") PROMPT_FILE=".github/prompt/release_note_prompt.txt"
USER_CONTENT="$(printf "TAG: %s\nARTIFACTS: %s\n\n提交列表:\n%s" "$TAG" "$ARTIFACTS_LIST" "$COMMITS")" SYSTEM_PROMPT=$(<"$PROMPT_FILE")
SYSTEM_PROMPT="$(jq -Rs . < "$PROMPT_FILE")" USER_CONTENT="TAG: $TAG\n提交列表:\n$COMMITS"
BODY=$(jq -n \ BODY=$(jq -n \
--arg system "$SYSTEM_PROMPT" \ --arg system "$SYSTEM_PROMPT" \
@ -118,49 +104,31 @@ jobs:
'{model: env.OPENROUTER_MODEL, messages:[{role:"system", content:$system},{role:"user", content:$user}], temperature:0.2, max_tokens:800}') '{model: env.OPENROUTER_MODEL, messages:[{role:"system", content:$system},{role:"user", content:$user}], temperature:0.2, max_tokens:800}')
RESPONSE=$(curl -s -X POST "$OPENROUTER_API_URL" \ RESPONSE=$(curl -s -X POST "$OPENROUTER_API_URL" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $OPENROUTER_API_KEY" \ -H "Authorization: Bearer $OPENROUTER_API_KEY" \
-H "Content-Type: application/json" \
-d "$BODY") -d "$BODY")
echo "$RESPONSE" | jq -r '.choices[0].message.content // .choices[0].text // ""' > /tmp/release_body.txt || true echo "=== OpenRouter raw response ==="
echo "=== generated release note ===" echo "$RESPONSE" | jq .
sed -n '1,200p' /tmp/release_body.txt || true
- name: Create or update release & upload assets RELEASE_BODY=$(echo "$RESPONSE" | jq -r '.choices[0].message.content // .choices[0].text // ""')
env:
GHTOKEN: ${{ secrets.GITHUB_TOKEN }} if [ -z "$RELEASE_BODY" ]; then
REPO: ${{ github.repository }} echo "❌ OpenRouter failed to generate release note, terminating workflow."
TAG: "${{ github.ref_name }}" exit 1
run: |
set -euo pipefail
BODY=$(sed 's/"/\\"/g' /tmp/release_body.txt || echo "Automated release")
# check existing release for this tag
EXIST=$(curl -s -H "Authorization: token $GHTOKEN" "https://api.github.com/repos/$REPO/releases/tags/$TAG" || true)
RID=$(echo "$EXIST" | jq -r '.id // empty')
if [ -n "$RID" ]; then
echo "Update existing release id $RID"
jq -n --arg body "$BODY" '{body:$body}' > /tmp/update.json
curl -s -X PATCH -H "Authorization: token $GHTOKEN" -H "Content-Type: application/json" \
"https://api.github.com/repos/$REPO/releases/$RID" -d @/tmp/update.json | jq -r '.id'
else
echo "Create release for tag $TAG"
jq -n --arg tag "$TAG" --arg name "${RELEASE_NAME} $TAG" --arg body "$BODY" \
'{tag_name:$tag, name:$name, body:$body, draft:true, prerelease:false}' > /tmp/create.json
CREATE_RESP=$(curl -s -X POST -H "Authorization: token $GHTOKEN" -H "Content-Type: application/json" \
"https://api.github.com/repos/$REPO/releases" -d @/tmp/create.json)
RID=$(echo "$CREATE_RESP" | jq -r '.id')
fi fi
upload() { echo "$RELEASE_BODY" > CHANGELOG.md
f="$1" echo "=== generated release note ==="
[ -f "$f" ] || { echo "skip $f"; return; } cat CHANGELOG.md
NAME=$(basename "$f")
UPLOAD_URL=$(curl -s -H "Authorization: token $GHTOKEN" "https://api.github.com/repos/$REPO/releases/$RID" | jq -r '.upload_url')
UPLOAD_URL="${UPLOAD_URL%\{*}?name=${NAME}"
echo "Uploading $NAME..."
curl -s -X POST -H "Authorization: token $GHTOKEN" -H "Content-Type: application/zip" --data-binary @"$f" "$UPLOAD_URL" | jq -r '.id'
}
upload "./artifacts/NapCat.Framework.zip" - name: Create Release Draft and Upload Artifacts
upload "./artifacts/NapCat.Shell.zip" uses: softprops/action-gh-release@v1
echo "done" with:
name: NapCat ${{ github.ref_name }}
token: ${{ secrets.GITHUB_TOKEN }}
body_path: CHANGELOG.md
files: |
NapCat.Framework.zip
NapCat.Shell.zip
draft: true