#!/bin/bash # issue-create.sh - Create issues on Gitea or GitHub # Usage: issue-create.sh -t "Title" [-b "Body"] [-l "label1,label2"] [-m "milestone"] set -e SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" source "$SCRIPT_DIR/detect-platform.sh" # Default values TITLE="" BODY="" LABELS="" MILESTONE="" get_remote_host() { local remote_url remote_url=$(git remote get-url origin 2>/dev/null || true) if [[ -z "$remote_url" ]]; then return 1 fi if [[ "$remote_url" =~ ^https?://([^/]+)/ ]]; then echo "${BASH_REMATCH[1]}" return 0 fi if [[ "$remote_url" =~ ^git@([^:]+): ]]; then echo "${BASH_REMATCH[1]}" return 0 fi return 1 } get_gitea_token() { local host="$1" if [[ -n "${GITEA_TOKEN:-}" ]]; then echo "$GITEA_TOKEN" return 0 fi local creds="$HOME/.git-credentials" if [[ -f "$creds" ]]; then local token token=$(grep -F "$host" "$creds" 2>/dev/null | sed -n 's#https\?://[^@]*:\([^@/]*\)@.*#\1#p' | head -n 1) if [[ -n "$token" ]]; then echo "$token" return 0 fi fi return 1 } gitea_issue_create_api() { local host repo token url payload host=$(get_remote_host) || { echo "Error: could not determine remote host for API fallback" >&2 return 1 } repo=$(get_repo_info) || { echo "Error: could not determine repo owner/name for API fallback" >&2 return 1 } token=$(get_gitea_token "$host") || { echo "Error: Gitea token not found for API fallback (set GITEA_TOKEN or configure ~/.git-credentials)" >&2 return 1 } if [[ -n "$LABELS" || -n "$MILESTONE" ]]; then echo "Warning: API fallback currently applies title/body only; labels/milestone require authenticated tea setup." >&2 fi payload=$(TITLE="$TITLE" BODY="$BODY" python3 - <<'PY' import json import os payload = {"title": os.environ["TITLE"]} body = os.environ.get("BODY", "") if body: payload["body"] = body print(json.dumps(payload)) PY ) url="https://${host}/api/v1/repos/${repo}/issues" curl -fsS -X POST \ -H "Authorization: token ${token}" \ -H "Content-Type: application/json" \ -d "$payload" \ "$url" } usage() { cat <&2 usage ;; esac done if [[ -z "$TITLE" ]]; then echo "Error: Title is required (-t)" >&2 usage fi PLATFORM=$(detect_platform) case "$PLATFORM" in github) CMD="gh issue create --title \"$TITLE\"" [[ -n "$BODY" ]] && CMD="$CMD --body \"$BODY\"" [[ -n "$LABELS" ]] && CMD="$CMD --label \"$LABELS\"" [[ -n "$MILESTONE" ]] && CMD="$CMD --milestone \"$MILESTONE\"" eval "$CMD" ;; gitea) if command -v tea >/dev/null 2>&1; then CMD="tea issue create --title \"$TITLE\"" [[ -n "$BODY" ]] && CMD="$CMD --description \"$BODY\"" [[ -n "$LABELS" ]] && CMD="$CMD --labels \"$LABELS\"" # tea accepts milestone by name directly (verified 2026-02-05) [[ -n "$MILESTONE" ]] && CMD="$CMD --milestone \"$MILESTONE\"" if eval "$CMD"; then exit 0 fi echo "Warning: tea issue create failed, trying Gitea API fallback..." >&2 fi gitea_issue_create_api ;; *) echo "Error: Could not detect git platform" >&2 exit 1 ;; esac