From 9171e41e3390d52e2597c5393bc0b87f256db544 Mon Sep 17 00:00:00 2001 From: shokollm <270575765+shokollm@users.noreply.github.com> Date: Wed, 1 Apr 2026 23:23:34 +0000 Subject: [PATCH] feat(kugetsu): add queue infrastructure for autonomous PM Add queue management system for task queue architecture (Phase 1): - Add QUEUE_FILE and POLL_INTERVAL constants - Add init_queue() to initialize queue.json if missing - Add cmd_queue with subcommands: - list: Show queue status with counts per tier - enqueue : Add task to queue - dequeue [tier]: Remove and return next task (priority order) - clear: Clear all queued tasks Queue tiers: - dev_followups (highest priority) - user_interrupts (medium) - background (lowest) This enables the autonomous queue-based architecture where PM agent continuously polls the queue and assigns work to dev agents. Part of #49 Related to #46 (verbosity control) --- skills/kugetsu/scripts/kugetsu | 115 +++++++++++++++++++++++++++++++++ 1 file changed, 115 insertions(+) diff --git a/skills/kugetsu/scripts/kugetsu b/skills/kugetsu/scripts/kugetsu index 24152c1..481aeed 100755 --- a/skills/kugetsu/scripts/kugetsu +++ b/skills/kugetsu/scripts/kugetsu @@ -8,7 +8,9 @@ REPOS_CONFIG="$KUGETSU_DIR/repos.json" INDEX_FILE="$KUGETSU_DIR/index.json" NOTIFICATIONS_FILE="$KUGETSU_DIR/notifications.json" LOGS_DIR="$KUGETSU_DIR/logs" +QUEUE_FILE="$KUGETSU_DIR/queue.json" MAX_CONCURRENT_AGENTS="${MAX_CONCURRENT_AGENTS:-3}" +POLL_INTERVAL="${POLL_INTERVAL:-600}" # Load user config overrides (~/.kugetsu/config) if [ -f "$KUGETSU_DIR/config" ]; then @@ -544,6 +546,116 @@ cmd_logs() { done } +init_queue() { + if [ ! -f "$QUEUE_FILE" ]; then + cat > "$QUEUE_FILE" << 'EOF' +{ + "dev_followups": [], + "user_interrupts": [], + "background": [] +} +EOF + fi +} + +cmd_queue() { + local action="${1:-}" + + init_queue + + case "$action" in + ""|"list") + local total=0 + echo "Queue status:" + for tier in dev_followups user_interrupts background; do + local count=$(python3 -c "import json; d=json.load(open('$QUEUE_FILE')); print(len(d.get('$tier', [])))" 2>/dev/null || echo 0) + total=$((total + count)) + if [ "$count" -eq 0 ]; then + echo " $tier (0): (empty)" + else + echo " $tier ($count):" + python3 -c "import json, sys; d=json.load(open('$QUEUE_FILE')); [print(f' [{t[\"id\"]}] {t[\"message\"][:60]}') for t in d.get('$tier', [])]" 2>/dev/null || echo " (error reading)" + fi + done + echo "Total queued: $total" + ;; + "enqueue") + local tier="${2:-}" + local message="${3:-}" + if [ -z "$tier" ] || [ -z "$message" ]; then + echo "Usage: kugetsu queue enqueue " >&2 + echo " tier: dev_followups, user_interrupts, or background" >&2 + exit 1 + fi + if [[ ! "$tier" =~ ^(dev_followups|user_interrupts|background)$ ]]; then + echo "Error: Invalid tier '$tier'" >&2 + echo " Valid tiers: dev_followups, user_interrupts, background" >&2 + exit 1 + fi + local id="qe-$(date +%s)-$$" + python3 << EOF +import json +with open('$QUEUE_FILE', 'r') as f: + d = json.load(f) +d.setdefault('$tier', []).append({ + 'id': '$id', + 'message': '$message', + 'created': '$(date -Iseconds)' +}) +with open('$QUEUE_FILE', 'w') as f: + json.dump(d, f, indent=2) +print('Enqueued to $tier: [$id] $message') +EOF + ;; + "dequeue") + local tier="${2:-}" + local result=$(python3 << EOF +import json +with open('$QUEUE_FILE', 'r') as f: + d = json.load(f) +tiers = ['dev_followups', 'user_interrupts', 'background'] if not '$tier' else ['$tier'] +for t in tiers: + if d.get(t) and len(d[t]) > 0: + task = d[t].pop(0) + with open('$QUEUE_FILE', 'w') as f: + json.dump(d, f, indent=2) + print(f'{t}|{task["id"]}|{task["message"]}') + break +else: + print('Queue empty') +EOF +) + if [ "$result" = "Queue empty" ]; then + echo "$result" + exit 1 + fi + echo "$result" + ;; + "clear") + cat > "$QUEUE_FILE" << 'EOF' +{ + "dev_followups": [], + "user_interrupts": [], + "background": [] +} +EOF + echo "Queue cleared" + ;; + *) + echo "Usage: kugetsu queue " >&2 + echo "" >&2 + echo "Commands:" >&2 + echo " list Show queue status" >&2 + echo " enqueue Add task to queue" >&2 + echo " dequeue [tier] Remove and return next task" >&2 + echo " clear Clear all queued tasks" >&2 + echo "" >&2 + echo "Tiers: dev_followups, user_interrupts, background" >&2 + exit 1 + ;; + esac +} + cmd_doctor() { local fix=false @@ -1174,6 +1286,9 @@ main() { status) cmd_status ;; + queue) + cmd_queue "$@" + ;; doctor) cmd_doctor "$@" ;;