<?php

namespace Kanews\Kai\Tasks;

use Kanews\Kai\AI\Client;
use Kanews\Kai\Manager;
use Kanews\Kai\Support\Credits;
use Kanews\Kai\Support\ImageHelper;
use Kanews\Kai\Support\Options;

class AjaxTaskController
{
    private $manager;

    public function __construct(Manager $manager)
    {
        $this->manager = $manager;
    }

    public function register(): void
    {
        add_action('wp_ajax_generate_tts', [$this, 'generateTts']);
        add_action('wp_ajax_generate_featured_image', [$this, 'generateFeaturedImage']);
        add_action('wp_ajax_generate_hero_image', [$this, 'generateHeroImage']);
        add_action('wp_ajax_generate_comments', [$this, 'generateComments']);
        add_action('wp_ajax_generate_excerpt', [$this, 'generateExcerpt']);
        add_action('wp_ajax_generate_summary', [$this, 'generateSummary']);
        add_action('wp_ajax_generate_seo_title', [$this, 'generateSeoTitle']);
        add_action('wp_ajax_generate_article', [$this, 'generateArticle']);
        add_action('wp_ajax_generate_faq', [$this, 'generateFaq']);
        add_action('wp_ajax_generate_paraphrase', [$this, 'generateParaphrase']);
        add_action('wp_ajax_generate_translate', [$this, 'generateTranslate']);
    }

    public function generateTts(): void
    {
        $this->verifyNonce();

        $postId  = intval($_POST['post_id'] ?? 0);
        $this->ensureCanEditPost($postId);
        $voice   = sanitize_text_field($_POST['voice'] ?? 'alloy');
        $content = get_post_field('post_content', $postId);

        if (!$postId || empty($content)) {
            wp_send_json_error(['message' => __('Geçersiz yazı.', 'kanews')]);
        }

        if (!Credits::reduce(Credits::calculateFromContent($content))) {
            wp_send_json_error(['error' => false, 'message' => __('Krediniz yetmedi, kendi api keyinizi kullanın.', 'kanews')]);
        }

        try {
            $audio = $this->manager->ai()->tts(wp_strip_all_tags(strip_shortcodes($content)), $voice);
            $uploadDir = wp_upload_dir();
            $filePath  = $uploadDir['path'] . "/post-$postId.mp3";
            file_put_contents($filePath, $audio);

            $filetype = wp_check_filetype(basename($filePath), null);

            $attachmentId = wp_insert_attachment([
                'guid'           => $uploadDir['url'] . '/' . basename($filePath),
                'post_mime_type' => $filetype['type'],
                'post_title'     => preg_replace('/\.[^.]+$/', '', basename($filePath)),
                'post_content'   => '',
                'post_status'    => 'inherit',
            ], $filePath, $postId);

            $attachData = wp_generate_attachment_metadata($attachmentId, $filePath);
            wp_update_attachment_metadata($attachmentId, $attachData);

            $fileUrl = $uploadDir['url'] . "/post-$postId.mp3";
            update_post_meta($postId, 'post_text_to_speech', ['url' => $fileUrl, 'id' => $attachmentId]);

            wp_send_json_success([
                'message'  => __('Ses dosyası oluşturuldu.', 'kanews'),
                'file_url' => $fileUrl,
                'file_id'  => $attachmentId,
            ]);
        } catch (\Throwable $th) {
            $this->respondWithAiError($th);
        }
    }

    public function generateFeaturedImage(): void
    {
        $this->verifyNonce();

        $topic    = sanitize_text_field($_POST['topic'] ?? '');
        $postId   = intval($_POST['post_id'] ?? 0);
        $this->ensureCanEditPost($postId);
        $selected = $_POST['selected_image'] ?? null;

        if (empty($topic) || empty($postId)) {
            wp_send_json_error(['message' => __('Konu ve yazı ID\'si gereklidir.', 'kanews')]);
        }

        if (!empty($selected) && is_string($selected)) {
            $selected = json_decode(stripslashes($selected), true);
        }

        if (!empty($selected['url'])) {
            $imageId = ImageHelper::uploadFeaturedImage($selected, $postId);
            if ($imageId) {
                wp_send_json_success([
                    'message'   => __('Görsel başarıyla eklendi.', 'kanews'),
                    'image_id'  => $imageId,
                    'image_url' => wp_get_attachment_url($imageId),
                ]);
            }
        }

        $provider = sanitize_text_field($_POST['provider'] ?? Options::getDefaultProvider());
        $prompt = sprintf(
            'Ultra-realistic editorial news photograph of: %s. Shot on professional DSLR with 35mm lens, shallow depth of field, accurate skin tones and textures, natural lighting, true-to-life colors, photojournalism style. No illustrations, no CGI, no painting, no cartoons, no overlays, no text, no watermarks, no logos.',
            $topic
        );

        $bytes = $provider === 'gemini'
            ? ImageHelper::geminiImage($prompt)
            : ImageHelper::dalleImage($prompt, '1024x1024');

        $fallbackUsed = false;
        $fallbackMessage = '';

        if (is_wp_error($bytes)) {
            $errorMessage = $bytes->get_error_message();
            $openAiKey = Options::getApiKey('openai');
            $geminiKey = Options::getApiKey('gemini');
            $isSafetyError = stripos($errorMessage, 'safety') !== false || stripos($errorMessage, 'not allowed') !== false;

            if ($provider === 'gemini' && !empty($openAiKey)) {
                $fallback = ImageHelper::dalleImage($prompt, '1024x1024');
                if (!is_wp_error($fallback) && !empty($fallback)) {
                    $bytes = $fallback;
                    $fallbackUsed = true;
                    $fallbackMessage = sprintf(
                        __('Gemini görsel API hatası (%s). OpenAI DALL·E ile üretildi.', 'kanews'),
                        $errorMessage
                    );
                } else {
                    $fallbackError = is_wp_error($fallback) ? $fallback->get_error_message() : $errorMessage;
                    wp_send_json_error(['message' => $fallbackError]);
                }
            } elseif ($provider === 'openai' && $isSafetyError && !empty($geminiKey)) {
                $fallback = ImageHelper::geminiImage($prompt);
                if (!is_wp_error($fallback) && !empty($fallback)) {
                    $bytes = $fallback;
                    $fallbackUsed = true;
                    $fallbackMessage = __('OpenAI güvenlik filtresi tetiklendi. Gemini ile üretildi.', 'kanews');
                } else {
                    $fallbackError = is_wp_error($fallback) ? $fallback->get_error_message() : $errorMessage;
                    wp_send_json_error(['message' => $fallbackError]);
                }
            } else {
                wp_send_json_error(['message' => $errorMessage]);
            }
        }

        if ($bytes) {
            $imageId = ImageHelper::uploadFeaturedImageFromBytes($bytes, $postId, sanitize_file_name($topic) . '-kai.jpg');
            if ($imageId) {
                wp_send_json_success([
                    'message'   => $fallbackUsed
                        ? $fallbackMessage
                        : __('Görsel başarıyla üretildi ve yazıya eklendi.', 'kanews'),
                    'image_id'  => $imageId,
                    'image_url' => wp_get_attachment_url($imageId),
                ]);
            }
        }

        wp_send_json_error(['message' => __('Görsel üretilemedi. Lütfen daha sonra tekrar deneyin.', 'kanews')]);
    }

    public function generateHeroImage(): void
    {
        $this->verifyNonce();

        $postId = intval($_POST['post_id'] ?? 0);
        $this->ensureCanEditPost($postId);

        // Önce gönderilen manşet görsel ID'sini al
        $imageId = intval($_POST['image_id'] ?? 0);
        $originalImageId = $imageId;
        $sourceField = sanitize_text_field($_POST['source_field'] ?? 'manset_desktop'); // Hangi alandan alındı
        $title = stripslashes(sanitize_text_field($_POST['title'] ?? ''));
        $subtitle = stripslashes(sanitize_text_field($_POST['subtitle'] ?? ''));
        $textColor = sanitize_text_field($_POST['text_color'] ?? '#ffffff');
        $bgColor = sanitize_text_field($_POST['bg_color'] ?? '#000000');
        $bgOpacity = intval($_POST['bg_opacity'] ?? 70);

        // İmza / logo ayarları
        $signatureImageId = intval($_POST['signature_image_id'] ?? 0);
        $signaturePosition = sanitize_text_field($_POST['signature_position'] ?? 'top_right');
        if (!in_array($signaturePosition, ['top_left', 'top_right'], true)) {
            $signaturePosition = 'top_right';
        }

        // Kırpma ayarları
        $cropWidth = intval($_POST['crop_width'] ?? 0);
        $cropHeight = intval($_POST['crop_height'] ?? 0);
        if ($cropWidth < 0) {
            $cropWidth = 0;
        }
        if ($cropHeight < 0) {
            $cropHeight = 0;
        }

        // İçerik hizalama (center, left, right)
        $textAlign = sanitize_text_field($_POST['text_align'] ?? 'center');
        if (!in_array($textAlign, ['center', 'left', 'right'], true)) {
            $textAlign = 'center';
        }
        
        // Source field'ı doğrula
        if (!in_array($sourceField, ['manset_desktop', 'manset_mobile'])) {
            $sourceField = 'manset_desktop';
        }

        // Eğer hedef alanda görsel yoksa, öne çıkarılan görseli kullanmayı dene
        if (!$imageId) {
            $imageId = get_post_thumbnail_id($postId);
            // Öne çıkarılan görsel kullanılıyorsa, sourceField'ı değiştirme
            // Kullanıcının seçtiği hedef alana (manset_desktop veya manset_mobile) kaydedilecek
        }

        if (!$imageId) {
            wp_send_json_error(['message' => __('Lütfen bir manşet görseli veya öne çıkarılan görsel ekleyin.', 'kanews')]);
        }

        if (empty($title) && empty($subtitle)) {
            wp_send_json_error(['message' => __('En az bir başlık girmelisiniz.', 'kanews')]);
        }

        // Renk formatını kontrol et
        if (!preg_match('/^#[0-9a-fA-F]{6}$/', $textColor)) {
            $textColor = '#ffffff';
        }
        if (!preg_match('/^#[0-9a-fA-F]{6}$/', $bgColor)) {
            $bgColor = '#000000';
        }

        // Şeffaflığı sınırla
        $bgOpacity = max(0, min(100, $bgOpacity));

        // GD ile görsel üzerine metin ekleme
        $result = ImageHelper::createHeroImageWithText(
            $imageId,
            $title,
            $subtitle,
            $textColor,
            $bgColor,
            $bgOpacity,
            $postId,
            $signatureImageId,
            $signaturePosition,
            $cropWidth,
            $cropHeight,
            $textAlign,
            $sourceField
        );

        if (is_wp_error($result)) {
            wp_send_json_error(['message' => $result->get_error_message()]);
        }

        if (!$result) {
            wp_send_json_error(['message' => __('Görsel oluşturulamadı.', 'kanews')]);
        }

        // Meta değerini güncelle - oluşturulan görseli kaynak alana kaydet
        $imageUrl = wp_get_attachment_url($result);
        $thumbnailUrl = wp_get_attachment_image_url($result, 'thumbnail');
        if (!$thumbnailUrl) {
            $thumbnailUrl = $imageUrl;
        }
        
        // CSF 'unserialize' modunda çalışıyor, her field için ayrı meta key kullanılıyor
        // Media field formatı: array ['id' => int, 'url' => string, 'thumbnail' => string]
        // WordPress otomatik olarak serialize eder
        $mediaData = [
            'id' => $result,
            'url' => $imageUrl,
            'thumbnail' => $thumbnailUrl,
        ];
        
        // Kaynak alana oluşturulan görseli kaydet (unserialize modunda direkt field key'ine)
        // Bu CSF'nin get_meta_value fonksiyonunun okuduğu yer
        update_post_meta($postId, $sourceField, $mediaData);

        wp_send_json_success([
            'message' => __('Manşet görseli başarıyla oluşturuldu.', 'kanews'),
            'image_id' => $result,
            'image_url' => $imageUrl,
            'source_field' => $sourceField, // Hangi alana kaydedildiğini döndür
        ]);
    }

    public function generateComments(): void
    {
        $this->verifyNonce();
        $postId = intval($_POST['post_id'] ?? 0);
        $this->ensureCanEditPost($postId);
        $count  = intval($_POST['count'] ?? 5);

        $content = get_post_field('post_content', $postId);
        $title   = get_post_field('post_title', $postId);

        if (empty($content)) {
            wp_send_json_error(['message' => __('Yazı içeriği boş olamaz.', 'kanews')]);
        }

        $count = min($count, 20);

        if (!Credits::reduce($count)) {
            wp_send_json_error(['error' => false, 'message' => __('Krediniz yetmedi, kendi api keyinizi kullanın.', 'kanews')]);
        }

        try {
            $response = $this->manager->ai()->chat('comments', [
                'text'   => wp_strip_all_tags(strip_shortcodes($content)),
                'count'  => $count,
                'title'  => $title,
                'provider' => $this->getProviderParam(),
            ]);

            $rawContent = $response['content'];
            $cleaned    = preg_replace('/```json\s*|\s*```/', '', $rawContent);
            $comments   = json_decode($cleaned, true);
            $added      = 0;

            if (is_array($comments)) {
                foreach ($comments as $comment) {
                    $commentId = wp_insert_comment([
                        'comment_post_ID'      => $postId,
                        'comment_author'       => $comment['name'] ?? '',
                        'comment_author_email' => $comment['email'] ?? '',
                        'comment_content'      => $comment['comment'] ?? '',
                        'comment_date'         => date('Y-m-d H:i:s', strtotime('-' . rand(1, 30) . ' days')),
                        'comment_approved'     => 1,
                    ]);
                    if ($commentId) {
                        $added++;
                    }
                }
            }

            wp_send_json_success([
                'message' => sprintf(__('%d yorum başarıyla eklendi.', 'kanews'), $added),
            ]);
        } catch (\Throwable $th) {
            $this->respondWithAiError($th);
        }
    }

    public function generateExcerpt(): void
    {
        $this->handlePostTextTask('excerpt', function ($postId, $content, $response) {
            $excerpt = $response['content'];
            wp_update_post([
                'ID'           => $postId,
                'post_excerpt' => esc_html($excerpt),
            ]);

            wp_send_json_success([
                'message' => esc_html($excerpt),
            ]);
        });
    }

    public function generateSummary(): void
    {
        $this->handlePostTextTask('summary', function ($postId, $content, $response) {
            $summary = trim($response['content']);
            update_post_meta($postId, 'kanews_post_summary', esc_html($summary));
            wp_send_json_success(['message' => __('Özet oluşturuldu.', 'kanews')]);
        });
    }

    public function generateSeoTitle(): void
    {
        $this->handlePostTextTask('seo-title', function ($postId, $content, $response) {
            $title = esc_html($response['content']);
            wp_update_post([
                'ID'         => $postId,
                'post_title' => $title,
            ]);

            wp_send_json_success([
                'message' => $title,
            ]);
        });
    }

    public function generateArticle(): void
    {
        $this->verifyNonce();
        $this->ensureCanCreatePosts();

        $topic  = sanitize_text_field($_POST['topic'] ?? '');
        $notes  = sanitize_textarea_field($_POST['notes'] ?? '');
        $style  = sanitize_text_field($_POST['style'] ?? 'news');
        $model  = isset($_POST['model']) ? sanitize_text_field($_POST['model']) : '';
        $lang   = sanitize_text_field($_POST['language'] ?? 'auto');
        $use5w1h= filter_var($_POST['use_5w1h'] ?? false, FILTER_VALIDATE_BOOLEAN);
        $useList= filter_var($_POST['use_list'] ?? false, FILTER_VALIDATE_BOOLEAN);
        $addFaq = filter_var($_POST['add_faq'] ?? false, FILTER_VALIDATE_BOOLEAN);
        $useTable=filter_var($_POST['use_tables'] ?? false, FILTER_VALIDATE_BOOLEAN);

        if (empty($topic)) {
            wp_send_json_error(['message' => __('Konu gereklidir.', 'kanews')]);
        }

        try {
            $context = [
                'topic'      => $topic,
                'notes'      => $notes,
                'style'      => $style,
                'language'   => $lang,
                'use_5w1h'   => $use5w1h,
                'use_list'   => $useList,
                'add_faq'    => $addFaq,
                'use_tables' => $useTable,
                'provider'   => $this->getProviderParam(),
            ];

            if (!empty($model)) {
                $context['model'] = $model;
            }

            $response = $this->manager->ai()->chat('article', $context);

            wp_send_json_success([
                'message' => $response['content'],
            ]);
        } catch (\Throwable $th) {
            $this->respondWithAiError($th);
        }
    }

    public function generateFaq(): void
    {
        $this->handlePostTextTask('faq', function ($postId, $content, $response) {
            wp_send_json_success([
                'message' => $response['content'],
            ]);
        }, [
            'count'    => intval($_POST['count'] ?? 5),
            'detailed' => filter_var($_POST['detailed'] ?? true, FILTER_VALIDATE_BOOLEAN),
        ]);
    }

    public function generateParaphrase(): void
    {
        $this->handlePostTextTask('paraphrase', function ($postId, $content, $response) {
            wp_send_json_success([
                'message' => $response['content'],
            ]);
        }, (function () {
            $context = [
                'level'               => sanitize_text_field($_POST['level'] ?? 'medium'),
                'preserve_keywords'   => filter_var($_POST['preserve_keywords'] ?? true, FILTER_VALIDATE_BOOLEAN),
                'preserve_structure'  => filter_var($_POST['preserve_structure'] ?? true, FILTER_VALIDATE_BOOLEAN),
                'improve_seo'         => filter_var($_POST['improve_seo'] ?? false, FILTER_VALIDATE_BOOLEAN),
            ];

            if (!empty($_POST['model'])) {
                $context['model'] = sanitize_text_field($_POST['model']);
            }

            return $context;
        })());
    }

    public function generateTranslate(): void
    {
        $translateTitle = filter_var($_POST['translate_title'] ?? true, FILTER_VALIDATE_BOOLEAN);

        $this->handlePostTextTask('translate', function ($postId, $content, $response) use ($translateTitle) {
            $translatedText = $response['content'];
            $translatedTitle = '';
            $translatedBody  = $translatedText;

            if ($translateTitle) {
                $lines = preg_split("/\\r\\n|\\n|\\r/", $translatedText);
                if (!empty($lines[0]) && stripos(trim($lines[0]), 'TITLE:') === 0) {
                    $translatedTitle = trim(substr($lines[0], strlen('TITLE:')));
                    $translatedBody  = trim(implode("\n", array_slice($lines, 1)));
                } elseif (!empty($lines[0]) && (empty($lines[1]) || trim($lines[1]) === '')) {
                    $translatedTitle = trim($lines[0]);
                    $translatedBody  = trim(implode("\n", array_slice($lines, 2)));
                }

                if (empty($translatedBody)) {
                    $translatedBody = $translatedText;
                }
            }

            wp_send_json_success([
                'message' => $translatedBody,
                'title'   => $translatedTitle,
            ]);
        }, (function () use ($translateTitle) {
            $context = [
                'target_language'  => sanitize_text_field($_POST['target_language'] ?? 'en'),
                'translate_title'  => $translateTitle,
                'preserve_html'    => true,
            ];

            if (!empty($_POST['model'])) {
                $context['model'] = sanitize_text_field($_POST['model']);
            }

            return $context;
        })());
    }

    private function handlePostTextTask(string $task, callable $callback, array $extraContext = []): void
    {
        $this->verifyNonce();

        $postId = intval($_POST['post_id'] ?? 0);
        $this->ensureCanEditPost($postId);
        $content = get_post_field('post_content', $postId);
        $title   = get_post_field('post_title', $postId);

        if (!$postId || empty($content)) {
            wp_send_json_error(['message' => __('Yazı içeriği boş olamaz.', 'kanews')]);
        }

        try {
            $preserveHtml = !empty($extraContext['preserve_html']);
            if ($preserveHtml) {
                unset($extraContext['preserve_html']);
            }

            $response = $this->manager->ai()->chat($task, array_merge([
                'text'     => $this->prepareContentForTask($content, $preserveHtml),
                'title'    => $title,
                'provider' => $this->getProviderParam(),
            ], $extraContext));

            $callback($postId, $content, $response);
        } catch (\Throwable $th) {
            $this->respondWithAiError($th);
        }
    }

    private function prepareContentForTask(string $content, bool $preserveHtml): string
    {
        if (!$preserveHtml) {
            return wp_strip_all_tags(strip_shortcodes($content));
        }

        $cleaned = wp_kses_post($content);

        if (function_exists('has_blocks') && has_blocks($content)) {
            $rendered = do_blocks($content);
            if (is_string($rendered) && trim($rendered) !== '') {
                $cleaned = $rendered;
            }
        }

        return trim($cleaned);
    }

    private function verifyNonce(): void
    {
        $nonce = $_POST['nonce'] ?? '';
        if (!wp_verify_nonce(sanitize_text_field($nonce), 'kanews_ai_nonce_action')) {
            wp_send_json_error(['message' => __('Güvenlik doğrulaması başarısız.', 'kanews')]);
        }
    }

    private function ensureCanEditPost(int $postId): void
    {
        if (!$postId || !current_user_can('edit_post', $postId)) {
            wp_send_json_error([
                'message' => __('Bu yazıyı düzenleme yetkiniz yok.', 'kanews'),
                'code'    => 'forbidden',
            ]);
        }
    }

    private function ensureCanCreatePosts(): void
    {
        if (!current_user_can('edit_posts')) {
            wp_send_json_error([
                'message' => __('Bu işlemi gerçekleştirme yetkiniz yok.', 'kanews'),
                'code'    => 'forbidden',
            ]);
        }
    }

    private function getProviderParam(): ?string
    {
        return isset($_POST['provider']) ? sanitize_text_field($_POST['provider']) : null;
    }

    private function respondWithAiError(\Throwable $th): void
    {
        $message = $th->getMessage();

        if ($this->isQuotaError($message)) {
            wp_send_json_error([
                'message' => __('Seçilen yapay zekâ sağlayıcısının API kotası doldu. Lütfen kendi API anahtarınızı girin veya daha sonra tekrar deneyin.', 'kanews'),
                'code'    => 'quota_exceeded',
            ]);
        }

        wp_send_json_error(['message' => $message ?: __('Beklenmeyen bir hata oluştu.', 'kanews')]);
    }

    private function isQuotaError(?string $message): bool
    {
        if (!$message) {
            return false;
        }

        $text = strtolower($message);
        $keywords = [
            'quota',
            'rate limit',
            'limit exceeded',
            'exceeded your current quota',
            'insufficient tokens',
            '429',
        ];

        foreach ($keywords as $keyword) {
            if (strpos($text, $keyword) !== false) {
                return true;
            }
        }

        return false;
    }
}

