"""
NVIDIA Nemotron API Models - ADR-036
====================================
2026-03-29 ogt: Nemotron Tool Calling 整合 (83.3% 精準度)

OpenAI 相容格式 - 用於 Tool Calling 任務
"""

from typing import Any

from pydantic import BaseModel, Field


class ToolFunction(BaseModel):
    """Tool Function 定義"""

    name: str = Field(..., description="Tool 函數名稱")
    arguments: str = Field(..., description="Tool 參數 (JSON 字串)")


class ToolCall(BaseModel):
    """Tool Call 結構"""

    id: str = Field(..., description="Tool Call ID")
    type: str = Field(default="function", description="Tool 類型")
    function: ToolFunction = Field(..., description="Tool 函數")


class NvidiaMessage(BaseModel):
    """NVIDIA API Message 結構"""

    role: str = Field(..., description="訊息角色 (assistant/user/system)")
    content: str | None = Field(default=None, description="訊息內容")
    tool_calls: list[ToolCall] | None = Field(
        default=None, description="Tool Calls (僅 assistant)"
    )


class NvidiaChoice(BaseModel):
    """NVIDIA API Choice 結構"""

    index: int = Field(default=0, description="選項索引")
    message: NvidiaMessage = Field(..., description="回應訊息")
    finish_reason: str | None = Field(
        default=None, description="結束原因 (stop/tool_calls)"
    )


class NvidiaUsage(BaseModel):
    """NVIDIA API Token 使用統計"""

    prompt_tokens: int = Field(default=0, description="輸入 Token 數")
    completion_tokens: int = Field(default=0, description="輸出 Token 數")
    total_tokens: int = Field(default=0, description="總 Token 數")


class NvidiaResponse(BaseModel):
    """NVIDIA Nemotron API 完整回應"""

    id: str = Field(..., description="回應 ID")
    object: str = Field(default="chat.completion", description="物件類型")
    created: int = Field(..., description="建立時間戳")
    model: str = Field(..., description="模型名稱")
    choices: list[NvidiaChoice] = Field(..., description="回應選項")
    usage: NvidiaUsage | None = Field(default=None, description="Token 使用統計")


# === Tool Calling 請求結構 ===


class ToolDefinition(BaseModel):
    """Tool 定義 (發送給 API)"""

    type: str = Field(default="function", description="Tool 類型")
    function: dict[str, Any] = Field(..., description="函數定義 (JSON Schema)")


class NvidiaToolCallRequest(BaseModel):
    """NVIDIA Tool Calling 請求"""

    model: str = Field(
        default="nvidia/nemotron-mini-4b-instruct",
        description="模型名稱 (2026-03-29 ogt: 修正為可用的 mini 模型)",
    )
    messages: list[dict[str, Any]] = Field(..., description="對話訊息")
    tools: list[ToolDefinition] = Field(..., description="可用 Tools")
    tool_choice: str | dict[str, Any] = Field(
        default="auto", description="Tool 選擇策略"
    )
    temperature: float = Field(default=0.0, description="溫度 (0.0 最確定性)")
    max_tokens: int = Field(default=1024, description="最大輸出 Token")


# === 驗證結果結構 ===


class ToolCallValidationResult(BaseModel):
    """Tool Call 驗證結果"""

    valid: bool = Field(..., description="是否有效")
    tool_name: str | None = Field(default=None, description="Tool 名稱")
    arguments: dict[str, Any] | None = Field(default=None, description="解析後參數")
    error: str | None = Field(default=None, description="錯誤訊息")
    raw_response: str | None = Field(default=None, description="原始回應 (debug)")


class NvidiaProviderResult(BaseModel):
    """NvidiaProvider 回傳結果"""

    success: bool = Field(..., description="是否成功")
    tool_calls: list[ToolCallValidationResult] = Field(
        default_factory=list, description="驗證後的 Tool Calls"
    )
    usage: NvidiaUsage | None = Field(default=None, description="Token 使用統計")
    latency_ms: float = Field(default=0.0, description="延遲 (毫秒)")
    error: str | None = Field(default=None, description="錯誤訊息")
    fallback_triggered: bool = Field(
        default=False, description="是否觸發 Fallback"
    )
