#!/bin/bash

# Wrapper script for copilot to get clickable focus notifications via swaync

set -euo pipefail

notify_focus() {
    local action="$1"
    local win_addr="$2"
    [ -n "$action" ] || return 0
    [ "$action" = "f" ] && [ -n "$win_addr" ] && hyprctl dispatch focuswindow address:"$win_addr" >/dev/null 2>&1 || true
}

notify_action_required() {
    local win_addr="$1"
    local action
    action=$(notify-send "Copilot" "✋ Action required" --action="f=Focus" -u critical -a "Copilot" -i ~/dl/copilot.png || true)
    notify_focus "$action" "$win_addr"
}

notify_task_finished() {
    local win_addr="$1"
    local action
    action=$(notify-send "Copilot" "✅ Task finished" --action="f=Focus" -u normal -a "Copilot" -i ~/dl/copilot.png || true)
    notify_focus "$action" "$win_addr"
}

start_interactive_monitor() {
    local win_addr="$1"
    local started_epoch="$2"
    local log_file
    local line
    local busy=0
    local ask_user_pending=0

    # Wait for the process log created by this copilot invocation.
    for _ in $(seq 1 60); do
        log_file=$(find "$HOME/.copilot/logs" -maxdepth 1 -name 'process-*.log' -newermt "@$started_epoch" -print 2>/dev/null | sort | tail -n1 || true)
        if [ -n "${log_file:-}" ]; then
            break
        fi
        sleep 0.1
    done

    [ -n "${log_file:-}" ] || return 0

    tail -n0 -F "$log_file" 2>/dev/null | while IFS= read -r line; do
        if [ "$ask_user_pending" -gt 0 ]; then
            ask_user_pending=$((ask_user_pending - 1))
        fi

        case "$line" in
        *"kind: assistant_turn_start"*)
            busy=1
            ;;
        *'"name": "ask_user"'*)
            # "ask_user" appears in tool schema on every turn; only alert if a
            # real tool call follows immediately with a question payload.
            ask_user_pending=8
            ;;
        *'"arguments": "{\"question\":'*)
            if [ "$ask_user_pending" -gt 0 ]; then
                notify_action_required "$win_addr"
                ask_user_pending=0
            fi
            ;;
        *"kind: session_idle"*)
            if [ "$busy" -eq 1 ]; then
                notify_task_finished "$win_addr"
                busy=0
            fi
            ask_user_pending=0
            ;;
        esac
    done
}

is_prompt_run=0
for arg in "$@"; do
    case "$arg" in
    -p | --prompt | -i | --interactive)
        is_prompt_run=1
        break
        ;;
    esac
done

win_addr="$(hyprctl activewindow -j | jq -r '.address // empty')"

if [ "$is_prompt_run" -eq 0 ] || [ "$#" -eq 0 ]; then
    started_epoch=$(date +%s)

    if [ -d "$HOME/.copilot/logs" ]; then
        start_interactive_monitor "$win_addr" "$started_epoch" &
        monitor_pid=$!
        trap 'kill "$monitor_pid" 2>/dev/null || true' EXIT
    fi

    # Debug logs include structured telemetry markers needed by the monitor.
    has_log_level=0
    for arg in "$@"; do
        case "$arg" in
        --log-level | --log-level=*)
            has_log_level=1
            break
            ;;
        esac
    done

    set +e
    if [ "$has_log_level" -eq 1 ]; then
        copilot "$@"
    else
        copilot --log-level debug "$@"
    fi
    exit_code=$?
    set -e
    kill "${monitor_pid:-}" 2>/dev/null || true
    exit "$exit_code"
fi

copilot --output-format json "$@" |
    tee >(
        jq -Rrc '
     (fromjson? | select(. != null)) as $e |
     if $e.type=="result" then {"kind":"done","code":($e.exitCode // 0)}
     elif $e.type=="tool.execution_start" and ($e.data.toolName=="ask_user") then {"kind":"action"}
     else empty end
   ' |
            while read -r ev; do
                kind="$(jq -r '.kind' <<<"$ev")"
                if [ "$kind" = "action" ]; then
                    notify_action_required "$win_addr"
                else
                    notify_task_finished "$win_addr"
                fi
            done
    ) |
    jq -Rr '(fromjson? | select(.type=="assistant.message") | (.data.content // empty))'
