"""
Task Detection - Classify prompts into task types.

Detects task type from prompt using keyword matching with context awareness.
Task types: coding, analysis, reasoning, simple_qa, creative, general

Ported from _legacy/robot_resources/task_detection.py
"""

import re
from typing import Literal

TaskType = Literal["coding", "analysis", "reasoning", "simple_qa", "creative", "general"]

# Keyword patterns for each task type
# Multi-word phrases are checked first (higher priority)
# Single words use word boundary matching to avoid partial matches
TASK_PATTERNS: dict[TaskType, list[str]] = {
    "coding": [
        # Multi-word phrases (checked with substring)
        "write code",
        "write a function",
        "write a script",
        "write a program",
        "write python",
        "write javascript",
        "write typescript",
        "write java",
        "write in python",
        "write in javascript",
        "write in java",
        "python code",
        "javascript code",
        "typescript code",
        "fix the bug",
        "fix this bug",
        "debug this",
        "implement a",
        "implement the",
        "unit test",
        "integration test",
        "rest api",
        "api endpoint",
        "build a",
        "build an",
        # Single words (checked with word boundaries)
        "code",
        "function",
        "implement",
        "debug",
        "script",
        "program",
        "algorithm",
        "class",
        "method",
        "bug",
        "syntax",
        "compile",
        "refactor",
        "build",
        "python",
        "javascript",
        "typescript",
        "java",
        "rust",
        "go",
        "golang",
        "sql",
        "html",
        "css",
        "react",
        "vue",
        "angular",
        "nodejs",
        "django",
        "flask",
        "git",
        "docker",
        "kubernetes",
        "database",
        "regex",
        "websocket",
        "parse",
        "serialize",
        "deserialize",
    ],
    "reasoning": [
        # Multi-word phrases
        "explain why",
        "tell me why",
        "reason through",
        "think through",
        "step by step",
        "analyze the logic",
        "evaluate the argument",
        "problem solving",
        "critical thinking",
        "assess the validity",
        # Single words
        "why",
        "explain",
        "reason",
        "deduce",
        "prove",
        "logic",
        "logical",
        "therefore",
        "premise",
        "conclusion",
        "implies",
        "derive",
        "infer",
        "reasoning",
        "puzzle",
        "riddle",
        "paradox",
        "dilemma",
    ],
    "analysis": [
        # Multi-word phrases
        "pros and cons",
        "strengths and weaknesses",
        "compare and contrast",
        # Single words
        "analyze",
        "analyse",
        "examine",
        "evaluate",
        "assess",
        "review",
        "compare",
        "contrast",
        "breakdown",
        "dissect",
        "investigate",
        "research",
        "explore",
        "survey",
        "audit",
        "inspect",
        "scrutinize",
        "advantages",
        "disadvantages",
        "tradeoffs",
        "trade-offs",
        "swot",
        "metrics",
        "kpi",
        "benchmark",
        "trend",
        "insight",
    ],
    "simple_qa": [
        # Multi-word phrases (most important for Q&A)
        "what is",
        "what's",
        "who is",
        "who's",
        "where is",
        "where's",
        "when is",
        "when's",
        "how many",
        "how much",
        "how old",
        "how long",
        "what are",
        "who are",
        "where are",
        "when are",
        "give me",
        "tell me",
        "can you tell",
        "do you know",
        "true or false",
        "yes or no",
        "capital of",
        "population of",
        "price of",
        "cost of",
        "date of",
        "name of",
        "who invented",
        "who founded",
        "who created",
        "when was",
        "what does",
        "stand for",
        "does stand for",
        # Single words
        "define",
        "definition",
        "meaning",
        "translate",
        "convert",
        "calculate",
        "list",
        "weather",
        "temperature",
        "distance",
    ],
    "creative": [
        # Multi-word phrases
        "write a story",
        "write a poem",
        "write an essay",
        "write a blog",
        "write a song",
        "write lyrics",
        "short story",
        "creative writing",
        "come up with",
        "think of ideas",
        "marketing copy",
        # Single words
        "write",
        "create",
        "generate",
        "compose",
        "draft",
        "story",
        "poem",
        "essay",
        "article",
        "blog",
        "content",
        "script",
        "dialogue",
        "narrative",
        "fiction",
        "novel",
        "brainstorm",
        "ideate",
        "imagine",
        "slogan",
        "tagline",
        "headline",
        "brand",
        "marketing",
        "advertisement",
        "campaign",
        "pitch",
        "proposal",
        "song",
        "lyrics",
        "haiku",
        "sonnet",
    ],
}

# Priority order for task detection
# Coding first because it has specific language/tool keywords
TASK_PRIORITY: list[TaskType] = [
    "coding",  # Programming tasks (specific language/tool keywords)
    "creative",  # Creative tasks (write a story, etc.)
    "reasoning",  # Complex thinking tasks
    "analysis",  # Analytical tasks
    "simple_qa",  # Simple questions (broad, checked last)
]

# Context-aware overrides for ambiguous keywords
CONTEXT_OVERRIDES: dict[tuple[str, TaskType], list[str]] = {
    # "why" can be simple_qa (factual), coding (debugging), or reasoning
    ("why", "simple_qa"): [
        "capital",
        "population",
        "color",
        "name",
        "country",
        "city",
        "president",
        "currency",
        "language",
        "flag",
    ],
    ("why", "coding"): [
        "error",
        "bug",
        "crash",
        "exception",
        "fail",
        "failed",
        "failing",
        "broken",
        "not working",
        "doesn't work",
        "won't compile",
    ],
    # "explain" can be coding (technical) or reasoning (conceptual)
    ("explain", "coding"): [
        "code",
        "function",
        "async",
        "await",
        "class",
        "method",
        "algorithm",
        "syntax",
        "compile",
        "runtime",
        "api",
        "endpoint",
    ],
    # "write" can be coding or creative
    ("write", "coding"): [
        "function",
        "code",
        "script",
        "api",
        "program",
        "class",
        "method",
        "algorithm",
        "parser",
        "query",
        "regex",
    ],
    ("write", "creative"): [
        "story",
        "poem",
        "essay",
        "article",
        "blog",
        "song",
        "lyrics",
        "narrative",
        "fiction",
        "haiku",
        "sonnet",
    ],
    # "create" can be coding or creative
    ("create", "coding"): [
        "function",
        "code",
        "script",
        "api",
        "program",
        "class",
        "method",
        "algorithm",
        "microservice",
        "service",
        "endpoint",
        "database",
    ],
    # "compare" with "vs" is analysis
    ("compare", "analysis"): ["vs", "versus", "vs.", "compared to", "or", "better"],
    # "review" and "evaluate" can be analysis
    ("review", "analysis"): [
        "quality",
        "efficiency",
        "performance",
        "pros",
        "cons",
        "strengths",
        "weaknesses",
    ],
    ("evaluate", "analysis"): [
        "efficiency",
        "performance",
        "quality",
        "effectiveness",
        "pros",
        "cons",
    ],
}


def _is_word_match(keyword: str, text: str) -> bool:
    """
    Check if keyword matches in text with word boundaries.

    For multi-word phrases: uses substring match
    For single words: uses word boundary regex to avoid partial matches
    """
    if " " in keyword:
        return keyword in text
    else:
        pattern = r"\b" + re.escape(keyword) + r"\b"
        return bool(re.search(pattern, text))


def analyze_prompt_structure(prompt: str) -> dict:
    """
    Analyze the structural features of a prompt.

    Returns:
        Dict with structural features:
        - word_count: Number of words in prompt
        - has_question_mark: Whether prompt contains ?
        - has_code_block: Whether prompt contains ``` code blocks
        - has_inline_code: Whether prompt contains ` inline code
        - is_short_question: Short prompt with question mark
        - line_count: Number of lines in prompt
    """
    words = prompt.split()
    lines = prompt.strip().split("\n")

    has_code_block = "```" in prompt
    has_inline_code = "`" in prompt and not has_code_block
    has_question_mark = "?" in prompt

    return {
        "word_count": len(words),
        "has_question_mark": has_question_mark,
        "has_code_block": has_code_block,
        "has_inline_code": has_inline_code,
        "is_short_question": len(words) < 10 and has_question_mark,
        "line_count": len(lines),
    }


def detect_task_type(prompt: str) -> TaskType:
    """
    Detect task type from prompt using hybrid detection:
    1. Priority patterns (definitions, factual questions)
    2. Keyword matching
    3. Context-aware overrides for ambiguous keywords
    4. Structure-based adjustments

    Args:
        prompt: The user's prompt to analyze

    Returns:
        Detected task type (coding, analysis, reasoning, simple_qa, creative, general)
    """
    prompt_lower = prompt.lower()
    structure = analyze_prompt_structure(prompt)
    word_count = structure["word_count"]

    # STEP 0: Priority patterns - short factual/definition questions
    definition_patterns = [
        "what is ",
        "what's ",
        "what are ",
        "what does ",
        "what do ",
        "who is ",
        "who's ",
        "who are ",
        "who invented ",
        "who founded ",
        "who created ",
        "when is ",
        "when's ",
        "when was ",
        "when were ",
        "where is ",
        "where's ",
        "where are ",
    ]

    if word_count < 8:
        for pattern in definition_patterns:
            if prompt_lower.startswith(pattern):
                return "simple_qa"

    if "stand for" in prompt_lower and word_count < 10:
        return "simple_qa"

    # STEP 1: Initial keyword-based detection
    initial_task: TaskType | None = None
    for task_type in TASK_PRIORITY:
        keywords = TASK_PATTERNS[task_type]
        if any(_is_word_match(kw, prompt_lower) for kw in keywords):
            initial_task = task_type
            break

    if initial_task is None:
        return "general"

    # STEP 2: Apply context overrides for ambiguous keywords
    for (trigger_word, override_task), context_words in CONTEXT_OVERRIDES.items():
        if _is_word_match(trigger_word, prompt_lower):
            if any(_is_word_match(ctx, prompt_lower) for ctx in context_words):
                initial_task = override_task
                break

    # STEP 3: Structure-based adjustments
    is_simple_question = (
        structure["is_short_question"]
        and not structure["has_code_block"]
        and not structure["has_inline_code"]
    )
    if is_simple_question:
        if initial_task == "reasoning":
            factual_keywords = [
                "capital",
                "population",
                "color",
                "name",
                "country",
                "city",
                "president",
                "currency",
                "language",
                "flag",
                "temperature",
                "distance",
                "price",
                "cost",
                "date",
            ]
            has_factual = any(_is_word_match(kw, prompt_lower) for kw in factual_keywords)
            if has_factual:
                initial_task = "simple_qa"

    # Has code blocks → strongly suggest coding
    if structure["has_code_block"]:
        if initial_task not in ["coding"]:
            initial_task = "coding"

    # Long multi-line prompts are less likely to be simple_qa
    if structure["line_count"] > 5 and initial_task == "simple_qa":
        initial_task = "general"

    return initial_task


def get_task_confidence(prompt: str, task_type: TaskType) -> float:
    """
    Calculate confidence score for a task type detection.

    Returns:
        Confidence score between 0.0 and 1.0
    """
    if task_type == "general":
        return 0.5

    prompt_lower = prompt.lower()
    keywords = TASK_PATTERNS.get(task_type, [])

    matches = sum(1 for kw in keywords if _is_word_match(kw, prompt_lower))
    confidence = min(0.7 + (matches - 1) * 0.1, 0.95)

    return round(confidence, 2)


def analyze_prompt(prompt: str) -> dict:
    """
    Full prompt analysis returning task type and confidence.

    Returns:
        Dict with task_type, confidence, and matched_keywords
    """
    task_type = detect_task_type(prompt)
    confidence = get_task_confidence(prompt, task_type)

    prompt_lower = prompt.lower()
    keywords = TASK_PATTERNS.get(task_type, [])
    matched = [kw for kw in keywords if _is_word_match(kw, prompt_lower)]

    return {
        "task_type": task_type,
        "confidence": confidence,
        "matched_keywords": matched[:5],
    }
