#!/bin/bash

# Function to find the claude executable
find_claude() {
    set +e  # Disable exit on error within this function

    # First, try to load user's shell environment to get proper PATH
    # This is crucial when running from GUI apps which have minimal PATH
    # Use subshells to prevent returns/exits in profile files from affecting this function
    if [ -f "$HOME/.zshrc" ]; then
        (source "$HOME/.zshrc") &> /dev/null || true
        # Re-export PATH from a new shell that sources the profile
        eval "$(bash -c 'source "$HOME/.zshrc" 2>/dev/null && echo "export PATH=\"$PATH\""' 2>/dev/null || true)"
    elif [ -f "$HOME/.bashrc" ]; then
        (source "$HOME/.bashrc") &> /dev/null || true
        eval "$(bash -c 'source "$HOME/.bashrc" 2>/dev/null && echo "export PATH=\"$PATH\""' 2>/dev/null || true)"
    elif [ -f "$HOME/.bash_profile" ]; then
        (source "$HOME/.bash_profile") &> /dev/null || true
        eval "$(bash -c 'source "$HOME/.bash_profile" 2>/dev/null && echo "export PATH=\"$PATH\""' 2>/dev/null || true)"
    fi

    # Also try to load profile which is more commonly used on macOS
    if [ -f "$HOME/.profile" ]; then
        (source "$HOME/.profile") &> /dev/null || true
        eval "$(bash -c 'source "$HOME/.profile" 2>/dev/null && echo "export PATH=\"$PATH\""' 2>/dev/null || true)"
    fi

    # Check if claude is already in PATH (after loading shell environment)
    if command -v claude &> /dev/null; then
        command -v claude
        return 0
    fi

    # Try to source nvm and find claude
    if [ -f "$HOME/.nvm/nvm.sh" ]; then
        export NVM_DIR="$HOME/.nvm"
        (source "$NVM_DIR/nvm.sh") &> /dev/null || true
        eval "$(bash -c 'export NVM_DIR="$HOME/.nvm"; source "$NVM_DIR/nvm.sh" 2>/dev/null && echo "export PATH=\"$PATH\""' 2>/dev/null || true)"
        if command -v claude &> /dev/null; then
            command -v claude
            return 0
        fi
    fi

    # Try to source asdf if installed
    if [ -f "$HOME/.asdf/asdf.sh" ]; then
        (source "$HOME/.asdf/asdf.sh") &> /dev/null || true
        eval "$(bash -c 'source "$HOME/.asdf/asdf.sh" 2>/dev/null && echo "export PATH=\"$PATH\""' 2>/dev/null || true)"
        if command -v claude &> /dev/null; then
            command -v claude
            return 0
        fi
    fi

    # Check for Homebrew and add to PATH if found
    if [ -x "/opt/homebrew/bin/brew" ]; then
        eval "$(/opt/homebrew/bin/brew shellenv 2>/dev/null || true)"
    elif [ -x "/usr/local/bin/brew" ]; then
        eval "$(/usr/local/bin/brew shellenv 2>/dev/null || true)"
    fi

    # Check again after setting up Homebrew
    if command -v claude &> /dev/null; then
        command -v claude
        return 0
    fi

    # Check common npm global installation directories
    local common_paths=(
        # NVM installations
        "$HOME/.nvm/versions/node/*/bin/claude"
        # Homebrew node installations
        "/opt/homebrew/bin/claude"
        "/opt/homebrew/lib/node_modules/.bin/claude"
        "/usr/local/bin/claude"
        "/usr/local/lib/node_modules/.bin/claude"
        # npm global
        "$HOME/.npm-global/bin/claude"
        "$HOME/.npm/bin/claude"
        # Yarn global
        "$HOME/.config/yarn/global/node_modules/.bin/claude"
        "$HOME/.yarn/bin/claude"
        # pnpm global
        "$HOME/.local/share/pnpm/claude"
        "$HOME/Library/pnpm/claude"
        # asdf
        "$HOME/.asdf/shims/claude"
        # fnm
        "$HOME/.fnm/node-versions/*/installation/bin/claude"
        "$HOME/Library/Application Support/fnm/node-versions/*/installation/bin/claude"
        # volta
        "$HOME/.volta/bin/claude"
        # macOS user local
        "$HOME/.local/bin/claude"
        "/usr/bin/claude"
    )

    for path_pattern in "${common_paths[@]}"; do
        # Use ls to expand glob patterns, pick the most recent match
        local expanded_path=$(ls -t $path_pattern 2>/dev/null | head -n 1)
        if [ -n "$expanded_path" ] && [ -x "$expanded_path" ]; then
            echo "$expanded_path"
            return 0
        fi
    done

    set -e  # Re-enable exit on error
    return 1
}

# Enable exit on error for main script
set -e

# Find claude command
CLAUDE_CMD=$(find_claude) || true
if [ -z "$CLAUDE_CMD" ]; then
    echo "[error] Claude Code CLI not found." >&2
    echo "[error] " >&2
    echo "[error] Please install it with: npm install -g @anthropic-ai/claude-code" >&2
    echo "[error] " >&2
    echo "[error] Current PATH: $PATH" >&2
    echo "[error] HOME: $HOME" >&2
    echo "[error] " >&2
    echo "[error] If installed, ensure 'claude' is in your PATH by adding it to ~/.zshrc or ~/.bashrc" >&2
    exit 1
fi

# Read inputs from environment variables
REPO_PATH="$TOWER_EXTENSION_INPUT_REPOSITORYPATH"
USER_PROMPT="$TOWER_EXTENSION_INPUT_USERPROMPT"
PROMPT_INPUT="$TOWER_EXTENSION_INPUT_PROMPT"
CURRENT_MESSAGE="$TOWER_EXTENSION_INPUT_CURRENTMESSAGE"
FUNCTION_NAME="$TOWER_EXTENSION_FUNCTION"

# Determine which function to execute
if [ "$FUNCTION_NAME" = "rephraseCommitMessage" ]; then
    # REPHRASE MODE

    # Check if we have a current message
    if [ -z "$CURRENT_MESSAGE" ]; then
        echo "[error] No current message provided for rephrasing" >&2
        exit 1
    fi

    # Report progress
    echo "[progress] Analyzing commit message..." >&2

    FUNCTION_PROMPT="Rephrase the commit message per the user prompt. Only output the commit message string, no surrounding markdown or explanations."
    PROMPT="$FUNCTION_PROMPT

Context:
repositoryPath: $REPO_PATH
currentMessage:
\`\`\`
$CURRENT_MESSAGE
\`\`\`

User prompt:
$USER_PROMPT"

    # Report progress
    echo "[progress] Rephrasing commit message..." >&2

    if [ -n "$REPO_PATH" ]; then
        cd "$REPO_PATH"
    fi

    # Call Claude Code - it should only output the rephrased commit message
    COMMIT_MESSAGE=$("$CLAUDE_CMD" -p "$PROMPT" 2>/dev/null)

elif [ "$FUNCTION_NAME" = "generateFromPrompt" ]; then
    # GENERATE FROM PROMPT MODE

    # Check if we have a user prompt
    if [ -z "$USER_PROMPT" ]; then
        echo "[error] No prompt provided" >&2
        exit 1
    fi

    # Report progress
    echo "[progress] Generating commit message from prompt..." >&2

    DRAFT_MESSAGE="$CURRENT_MESSAGE"

    FUNCTION_PROMPT="Create a commit message based on the user prompt and the provided draft. Only access the repository if explicitly requested by the user. Only output the commit message string, no surrounding markdown or explanations."
    PROMPT="$FUNCTION_PROMPT

Context:
repositoryPath: $REPO_PATH
currentMessage:
\`\`\`
$CURRENT_MESSAGE
\`\`\`

User prompt:
$USER_PROMPT

Draft message:
\`\`\`
$DRAFT_MESSAGE
\`\`\`"

    if [ -n "$REPO_PATH" ]; then
        cd "$REPO_PATH"
    fi

    # Call Claude Code with just the prompt - it should only output the commit message
    COMMIT_MESSAGE=$("$CLAUDE_CMD" -p "$PROMPT" 2>/dev/null)

else
    # GENERATE MODE (default)

    # Report progress
    echo "[progress] Reading repository changes..." >&2

    # Report progress
    echo "[progress] Analyzing changes with Claude Code..." >&2

    FUNCTION_PROMPT="Generate a commit message based on the diff of staged changes. Follow the user prompt. Only output the commit message string, no surrounding markdown or explanations."
    PROMPT="$FUNCTION_PROMPT

Context:
repositoryPath: $REPO_PATH
currentMessage:
\`\`\`
$CURRENT_MESSAGE
\`\`\`

User prompt:
$USER_PROMPT"

    # Report progress
    echo "[progress] Generating commit message..." >&2

    if [ -n "$REPO_PATH" ]; then
        cd "$REPO_PATH"
    fi

    # Call Claude Code - it should only output the commit message
    COMMIT_MESSAGE=$("$CLAUDE_CMD" -p "$PROMPT" 2>/dev/null)
fi

# Check if we got a response
if [ -z "$COMMIT_MESSAGE" ]; then
    echo "[error] Failed to generate commit message" >&2
    exit 1
fi

# Output the commit message to stdout
echo "$COMMIT_MESSAGE"
