<?php
/**
 * Model Registry
 *
 * Centralized source of truth for model defaults, labels,
 * capabilities, and provider support across the plugin.
 *
 * @package WP_Agentic_Writer
 */

if (!defined("ABSPATH")) {
    exit();
}

/**
 * Class WPAW_Model_Registry
 *
 * Single source of truth for model configuration.
 *
 * Usage:
 *   $defaults = WPAW_Model_Registry::get_task_defaults();
 *   $registry = WPAW_Model_Registry::get_registry();
 */
class WPAW_Model_Registry
{
    /**
     * Task type constants.
     */
    const TASK_CHAT = "chat";
    const TASK_CLARITY = "clarity";
    const TASK_PLANNING = "planning";
    const TASK_WRITING = "writing";
    const TASK_EXECUTION = "execution";
    const TASK_REFINEMENT = "refinement";
    const TASK_ANALYSIS = "analysis";
    const TASK_SUMMARIZE = "summarize";
    const TASK_IMAGE = "image";

    /**
     * Get the complete model registry.
     *
     * Structure:
     *   'task_type' => [
     *     'default' => 'model_id',
     *     'fallback' => 'model_id',  // optional
     *     'label' => 'Human-readable name',
     *     'description' => 'What this model is used for',
     *     'supported_providers' => ['openrouter', 'local', 'codex'],  // optional
     *     'capabilities' => ['chat', 'streaming', 'vision'],  // optional
     *   ]
     *
     * @since 0.2.0
     * @return array Model registry.
     */
    public static function get_registry()
    {
        return [
            "chat" => [
                "default" => "google/gemini-2.5-flash",
                "fallback" => "google/gemini-2.0-flash-exp",
                "label" => "Chat Model",
                "description" => "Discussion, research, and recommendations",
                "capabilities" => ["chat", "streaming", "reasoning"],
            ],
            "clarity" => [
                "default" => "google/gemini-2.5-flash",
                "fallback" => "google/gemini-2.0-flash-exp",
                "label" => "Clarity Model",
                "description" => "Prompt analysis and quiz generation",
                "capabilities" => ["chat", "streaming"],
            ],
            "planning" => [
                "default" => "google/gemini-2.5-flash",
                "fallback" => "google/gemini-2.0-flash-exp",
                "label" => "Planning Model",
                "description" => "Article outline and structure generation",
                "capabilities" => ["chat", "streaming"],
            ],
            "writing" => [
                "default" => "anthropic/claude-3.5-haiku",
                "fallback" => "google/gemini-2.5-flash",
                "label" => "Writing Model",
                "description" => "Article content generation",
                "capabilities" => ["chat", "streaming", "long_context"],
            ],
            "execution" => [
                "default" => "anthropic/claude-3.5-haiku",
                "fallback" => "google/gemini-2.5-flash",
                "label" => "Execution Model",
                "description" => "Article section writing (alias for writing)",
                "capabilities" => ["chat", "streaming"],
            ],
            "refinement" => [
                "default" => "anthropic/claude-sonnet-4",
                "fallback" => "anthropic/claude-3.5-haiku",
                "label" => "Refinement Model",
                "description" => "Paragraph edits, rewrites, and improvements",
                "capabilities" => ["chat", "streaming"],
            ],
            "analysis" => [
                "default" => "google/gemini-2.5-flash",
                "fallback" => "anthropic/claude-3.5-haiku",
                "label" => "Analysis Model",
                "description" => "Content analysis and improvement suggestions",
                "capabilities" => ["chat", "streaming"],
            ],
            "summarize" => [
                "default" => "google/gemini-2.5-flash",
                "fallback" => "anthropic/claude-3.5-haiku",
                "label" => "Summarization Model",
                "description" => "Context summarization and compression",
                "capabilities" => ["chat"],
            ],
            "image" => [
                "default" => "openai/gpt-4o",
                "fallback" => "openai/dall-e-3",
                "label" => "Image Generation Model",
                "description" => "Image generation for articles",
                "capabilities" => ["image_generation"],
                "supported_providers" => ["openrouter"],
            ],
            "image_models" => [
                "black-forest-labs/flux-1.1-pro" => "FLUX 1.1 Pro",
                "black-forest-labs/flux-pro" => "FLUX Pro",
                "recraft-ai/recraft-v3" => "Recraft V3",
            ],
        ];
    }

    /**
     * Get default model for a task type.
     *
     * @since 0.2.0
     * @param string $task Task type (chat, planning, execution, etc).
     * @return string Default model ID.
     */
    public static function get_default_model($task)
    {
        $registry = self::get_registry();
        $task_data = $registry[$task] ?? $registry["chat"];
        return $task_data["default"];
    }

    /**
     * Get fallback model for a task type.
     *
     * @since 0.2.0
     * @param string $task Task type.
     * @return string Fallback model ID.
     */
    public static function get_fallback_model($task)
    {
        $registry = self::get_registry();
        $task_data = $registry[$task] ?? $registry["chat"];
        return $task_data["fallback"] ?? $task_data["default"];
    }

    /**
     * Get all task defaults as key-value pairs.
     *
     * @since 0.2.0
     * @return array Task => default_model pairs.
     */
    public static function get_task_defaults()
    {
        $registry = self::get_registry();
        $defaults = [];

        foreach ($registry as $task => $data) {
            $defaults[$task] = $data["default"];
        }

        return $defaults;
    }

    /**
     * Get activation defaults (for plugin activation).
     *
     * This returns the format expected by the settings option.
     *
     * @since 0.2.0
     * @return array Settings-compatible defaults.
     */
    public static function get_activation_defaults()
    {
        return [
            "planning_model" => self::get_default_model("planning"),
            "execution_model" => self::get_default_model("writing"),
            "image_model" => self::get_default_model("image"),
        ];
    }

    /**
     * Validate a model ID is in the registry.
     *
     * @since 0.2.0
     * @param string $model Model ID.
     * @return bool True if valid.
     */
    public static function is_valid_model($model)
    {
        foreach (self::get_registry() as $task_data) {
            if (
                $model === $task_data["default"] ||
                $model === $task_data["fallback"]
            ) {
                return true;
            }
        }
        return false;
    }

    /**
     * Get display name for a model ID.
     *
     * Extracts a human-readable name from model IDs like
     * "google/gemini-2.5-flash" -> "Google Gemini 2.5 Flash"
     *
     * @since 0.2.0
     * @param string $model_id Model ID.
     * @return string Human-readable display name.
     */
    public static function get_model_display_name($model_id)
    {
        if (empty($model_id)) {
            return "Unknown Model";
        }

        // Handle known model ID patterns
        $display_names = [
            "google/gemini-2.5-flash" => "Google Gemini 2.5 Flash",
            "google/gemini-2.0-flash-exp" => "Google Gemini 2.0 Flash",
            "google/gemini-2.0-flash-exp:free" => "Google Gemini 2.0 Flash",
            "anthropic/claude-sonnet-4" => "Anthropic Claude Sonnet 4",
            "anthropic/claude-3.5-sonnet" => "Anthropic Claude 3.5 Sonnet",
            "anthropic/claude-3.5-haiku" => "Anthropic Claude 3.5 Haiku",
            "openai/gpt-4o" => "OpenAI GPT-4o",
            "openai/dall-e-3" => "OpenAI DALL-E 3",
            "black-forest-labs/flux-schnell" => "Black Forest Flux Schnell",
        ];

        if (isset($display_names[$model_id])) {
            return $display_names[$model_id];
        }

        // Generate from model ID: "provider/model-name" -> "Provider Model Name"
        $parts = explode("/", $model_id);
        if (count($parts) >= 2) {
            $provider = ucfirst(str_replace("-", " ", $parts[0]));
            $name = ucwords(str_replace("-", " ", $parts[1]));
            return trim($provider . " " . $name);
        }

        return ucwords(str_replace("-", " ", $model_id));
    }

    /**
     * Get JavaScript-compatible registry for frontend.
     *
     * @since 0.2.0
     * @return array JS-safe registry data.
     */
    public static function get_frontend_data()
    {
        $registry = self::get_registry();
        $result = [];

        foreach ($registry as $task => $data) {
            $result[$task] = [
                "default" => $data["default"],
                "fallback" => $data["fallback"] ?? null,
                "label" => $data["label"],
            ];
        }

        return $result;
    }
}
