name: Triage Issue description: Analizza una issue con opencode e la classifica come bug o richiesta. inputs: issue-title: description: Titolo dell'issue. required: true issue-body: description: Corpo dell'issue. required: true issue-number: description: Numero dell'issue. required: true repository: description: Repository in formato owner/repo. required: true api-token: description: Token API Gitea. required: true gitea-host: description: URL del server Gitea. required: false default: "https://git.incloud.ovh" api-key: description: API key per opencode. required: true model: description: Modello AI in formato provider/model. required: false default: "" outputs: label: description: Label attribuita (bug o richiesta). value: ${{ steps.classifica.outputs.label }} comment: description: Commento di triage pubblicato. value: ${{ steps.classifica.outputs.comment }} runs: using: composite steps: - name: Configura autenticazione opencode shell: bash run: | set -euo pipefail if ! command -v jq &> /dev/null; then echo "jq non trovato, tentativo di installazione..." if command -v apt-get &> /dev/null; then apt-get update -qq && apt-get install -y -qq jq 2>&1 || true elif command -v apk &> /dev/null; then apk add --no-cache jq 2>&1 || true fi command -v jq &> /dev/null || { echo "ERRORE: impossibile installare jq."; exit 1; } fi mkdir -p ~/.local/share/opencode jq -n \ --arg provider "opencode-go" \ --arg key "${{ inputs.api-key }}" \ '{($provider): {type: "api", key: $key}}' > ~/.local/share/opencode/auth.json chmod 600 ~/.local/share/opencode/auth.json - name: Classifica issue id: classifica shell: bash run: | set -euo pipefail HOST="${{ inputs.gitea-host }}" TOKEN="${{ inputs.api-token }}" REPO="${{ inputs.repository }}" ISSUE_NUM="${{ inputs.issue-number }}" MODEL_ARG=() [ -n "${{ inputs.model }}" ] && MODEL_ARG=(--model "${{ inputs.model }}") BODY="$(echo "${{ inputs.issue-body }}" | head -c 10000)" [ "${#BODY}" -ge 10000 ] && BODY+=$'\n... (troncato)' read -r -d '' PROMPT << 'PROMPT_EOF' || true Sei un sistema di triage automatico per repository software. Analizza la seguente issue e classificala con UNA delle label disponibili: - "bug": malfunzionamento, errore, crash, anomalia, comportamento inaspettato - "richiesta": nuova funzionalità, miglioramento, refactoring, ottimizzazione, o dubbio Rispondi ESCLUSIVAMENTE con un JSON valido su una singola riga, senza nessun altro testo: {"label":"bug","comment":"Breve analisi in italiano..."} Titolo: ${{ inputs.issue-title }} Corpo: $BODY PROMPT_EOF OUTFILE="$GITHUB_WORKSPACE/opencode-triage.txt" opencode run "$PROMPT" "${MODEL_ARG[@]}" --dangerously-skip-permissions 2>&1 | tee "$OUTFILE" RESPONSE=$(cat "$OUTFILE") JSON="" if echo "$RESPONSE" | jq empty 2>/dev/null; then JSON="$RESPONSE" elif JSON=$(echo "$RESPONSE" | grep -oP '\{"label":\s*"(bug|richiesta)".*?"comment":\s*".*?"\s*}' | head -1); then : elif JSON=$(echo "$RESPONSE" | grep -oP '\{[^}]*\}' | head -1); then : fi if [ -z "$JSON" ] || ! echo "$JSON" | jq empty 2>/dev/null; then echo "WARN: Impossibile estrarre JSON valido, default a richiesta" LABEL="richiesta" COMMENT="Classificazione automatica non riuscita. Label impostata a richiesta per default." else LABEL=$(echo "$JSON" | jq -r '.label // "richiesta"') COMMENT=$(echo "$JSON" | jq -r '.comment // "Classificazione automatica."') fi case "$LABEL" in bug|richiesta) ;; *) echo "WARN: Label '$LABEL' sconosciuta, default a richiesta"; LABEL="richiesta" ;; esac echo "label=$LABEL" >> "$GITHUB_OUTPUT" { echo "comment<> "$GITHUB_OUTPUT" echo "Label determinata: $LABEL" LABEL_ID=$(curl -sS -f "$HOST/api/v1/repos/$REPO/labels" \ -H "Authorization: token $TOKEN" \ -H "Accept: application/json" \ 2>/dev/null | jq -r ".[] | select(.name==\"$LABEL\") | .id" | head -1) if [ -n "$LABEL_ID" ]; then curl -sS -X PUT "$HOST/api/v1/repos/$REPO/issues/$ISSUE_NUM/labels" \ -H "Authorization: token $TOKEN" \ -H "Content-Type: application/json" \ -d "{\"labels\":[$LABEL_ID]}" 2>/dev/null && \ echo "Label '$LABEL' applicata" || \ echo "WARN: Impossibile applicare la label '$LABEL'" else echo "WARN: Label '$LABEL' non trovata nel repo. Creala manualmente o passa un token con permessi." fi COMMENT_JSON=$(jq -n --arg body "$COMMENT" '{body: $body}') curl -sS -X POST "$HOST/api/v1/repos/$REPO/issues/$ISSUE_NUM/comments" \ -H "Authorization: token $TOKEN" \ -H "Content-Type: application/json" \ -d "$COMMENT_JSON" 2>/dev/null && \ echo "Commento pubblicato sull'issue #$ISSUE_NUM" || \ echo "WARN: Impossibile pubblicare il commento"