<?php

namespace AIPT\Utils;

/**
 * Prompt metinlerini formatlama ve temizleme işlemlerini yöneten sınıf
 * 
 * Tüm prompt temizleme ve formatlama işlemleri bu sınıfta toplanmıştır.
 * SOLID, DRY ve KISS prensiplerine uygun olarak tasarlanmıştır.
 */
class PromptFormatter {
    
    /**
     * Prompt içeriğini temizler ve API için hazırlar
     * 
     * @param string $content Temizlenecek prompt içeriği 
     * @return string Temizlenmiş içerik
     */
    public static function cleanContent(string $content): string {

       

        $containsHtml = preg_match('/<([a-z][a-z0-9]*)\b[^>]*>(.*?)<\/\1>/is', $content);
        
        if ($containsHtml) {

            $tags = [];
            $content = preg_replace_callback('/<([a-z][a-z0-9]*)\b[^>]*>(.*?)<\/\1>/is', function($matches) use (&$tags) {
                $placeholder = '##HTML_TAG_' . count($tags) . '##';
                $tags[$placeholder] = $matches[0];
                return $placeholder;
            }, $content);
        }
        

        $content = self::formatVariables($content);
        

        $content = str_replace('\\\\', '\\', $content);
        

        $content = stripslashes($content);
        

        $direct_replacements = [
            '"\\u2013"' => '"-"',
            '"\\u2019"' => '"\'',
            '\\u2013' => '-',
            '\\u2019' => '\'',
            '\u2013' => '-',
            '\u2019' => '\'',
            "\\u2013" => "-",
            "\\u2019" => "'"
        ];
        
        foreach ($direct_replacements as $search => $replace) {
            $content = str_replace($search, $replace, $content);
        }
        

        $content = preg_replace_callback('/(?:\\\\u|\\\\\\\\u)([0-9a-fA-F]{4})/', function($matches) {
            return html_entity_decode('&#x' . $matches[1] . ';', ENT_QUOTES, 'UTF-8');
        }, $content);
        

        $specialChars = [
            '\u2019' => "'", 
            '\u2018' => "'", 
            '\u201C' => '"', 
            '\u201D' => '"', 
            '\u2013' => '-', 
            '\u2014' => '--', 
            '\u00A0' => ' ', 
            '\u00AD' => '-', 
            '\u2026' => '...', 
        ];
        
        foreach ($specialChars as $unicodeChar => $replacement) {
            $content = str_replace($unicodeChar, $replacement, $content);
        }
        

        $content = html_entity_decode($content, ENT_QUOTES | ENT_HTML5, 'UTF-8');
        

        $content = preg_replace('/[-\*]?\s*(Attributes|Categories|Tags|Price):\s*$/m', '', $content);
        $content = preg_replace('/[-\*]?\s*(Attributes|Categories|Tags|Price):\s*\n/m', '', $content);
        

        $content = preg_replace('/\*\*([^*]+)(?!\*)/', '$1', $content); 
        $content = preg_replace('/\*([^*]+)(?!\*)/', '$1', $content);   
        

        $content = preg_replace('/([a-z])([A-Z])/', '$1 $2', $content);
        

        $content = preg_replace('/\s+([a-z])([A-Z])/', ' $1 $2', $content);
        

        $content = preg_replace('/:([^\s])/', ': $1', $content);
        

        $content = preg_replace('/([0-9])([a-zA-Z])/', '$1 $2', $content);
        

        if (!$containsHtml) {

            $content = str_replace('\\n', "\n", $content);
            $content = str_replace('\r\n', "\n", $content);
            $content = str_replace("\r\n", "\n", $content);
            $content = str_replace('\r', "\n", $content);
            $content = str_replace("\r", "\n", $content);
            

            $content = str_replace('\t', ' ', $content);
            $content = str_replace("\t", ' ', $content);
            

            $content = preg_replace('/[ ]+/', ' ', $content);
            

            $content = preg_replace('/\n{3,}/', "\n\n", $content);
            

            $content = preg_replace('/[ ]+\n/', "\n", $content);
            $content = preg_replace('/\n[ ]+/', "\n", $content);
        }
        

        $content = preg_replace('/- - /', '- ', $content);
        

        $final_replacements = [
            '\u2013' => '-',
            '\u2019' => "'",
            '\\u2013' => '-',
            '\\u2019' => "'"
        ];
        
        foreach ($final_replacements as $search => $replace) {
            $content = str_replace($search, $replace, $content);
        }
        

        if ($containsHtml && !empty($tags)) {
            foreach ($tags as $placeholder => $originalTag) {
                $content = str_replace($placeholder, $originalTag, $content);
            }
            

        }
        

        return trim($content);
    }
    
    /**
     * Değişkenleri formatlayarak ön ekler ekleyen fonksiyon
     * 
     * Örnek: {PRICE} değişkenini Price: {PRICE} şeklinde formatlar.
     * Eğer değişken boş ise hiçbir ön ek eklemez.
     * 
     * @param string $content Formatlama yapılacak içerik
     * @param array $replacements Değişkenlerin gerçek değerlerini içeren assoc array (opsiyonel)
     * @return string Değişkenleri formatlanmış içerik
     */
    public static function formatVariables(string $content, array $replacements = []): string {

        preg_match_all('/{([A-Za-z0-9_]+)}/', $content, $matches);
        
        if (empty($matches[0])) {
            return $content;
        }
        

        foreach ($matches[0] as $index => $fullMatch) {
            $variableName = $matches[1][$index];
            

            $variableValue = "";
            

            if (isset($replacements[$fullMatch])) {
                $variableValue = $replacements[$fullMatch];
            } else {

                $variableValue = $fullMatch;
            }
            

            if (empty($variableValue) || $variableValue === $fullMatch) {

                continue;
            }
            

            $systemVariables = ['max_length', 'max_short_length', 'language', 'style', 'title'];
            if (in_array(strtolower($variableName), $systemVariables, true)) {
                $content = str_replace($fullMatch, $variableValue, $content);
                continue;
            }
            

            $formattedName = implode(' ', array_map('ucfirst', array_map('strtolower', explode('_', $variableName))));
            

            $replacement = $formattedName . ': ' . $variableValue;
            

            $content = str_replace($fullMatch, $replacement, $content);
        }
        
        return $content;
    }
    
    /**
     * AI'dan gelen metni WordPress editörü için düzgün formatlama
     * 
     * @param string $text AI'dan gelen ham metin
     * @return string WordPress editörü için formatlanmış metin
     */
    public static function formatAiResponseForWordPress($text) {

         $text = preg_replace('/^\s*```[a-zA-Z]*\s*\n/', '', $text); 
         $text = preg_replace('/\n\s*```\s*$/', '', $text); 

         $trimmed = ltrim( $text );
         if ( '' !== $trimmed && '<' === $trimmed[0] && preg_match( '/^<[a-zA-Z][a-zA-Z0-9]*\b/', $trimmed ) ) {
             $first_gt = strpos( $trimmed, '>', 0 );
             $first_lt = strpos( $trimmed, '<', 1 );

             if ( false === $first_gt || ( false !== $first_lt && $first_lt < $first_gt ) ) {

                 $text = ltrim( $text );
                 $text = substr( $text, 1 );
             }
         }

         $hasHtml = preg_match('/<[a-zA-Z][^>]*>/', $text);

        if ($hasHtml) {

            return wp_kses_post($text);
        }

        $text = preg_replace('/\*\*\*(.*?)\*\*\*/s', '<strong><em>$1</em></strong>', $text);
        $text = preg_replace('/\*\*(.*?)\*\*/s', '<strong>$1</strong>', $text);
        $text = preg_replace('/\*(.*?)\*/s', '<em>$1</em>', $text);
        

        $lines = explode("\n", $text);
        $in_list = false;
        $list_type = '';
        $formatted_lines = [];
        
        foreach ($lines as $line) {

            $line = preg_replace('/```[a-zA-Z]*/', '', $line);
            $line = preg_replace('/```/', '', $line);
            
            $trimmed = trim($line);
            

            if (!empty($trimmed)) {

                $trimmed = sanitize_text_field($trimmed);
                

                if (preg_match('/^#+\s+(.+)$/', $trimmed, $matches)) {
                    $headerLevel = strlen(trim($matches[0])) - strlen(trim($matches[1]));
                    if ($headerLevel >= 1 && $headerLevel <= 3) {

                        if ($in_list) {
                            $in_list = false;
                            $formatted_lines[] = $list_type === 'ul' ? '</ul>' : '</ol>';
                            $list_type = '';
                        }
                        $formatted_lines[] = '<h' . ($headerLevel + 1) . '>' . esc_html($matches[1]) . '</h' . ($headerLevel + 1) . '>';
                        continue;
                    }
                }
                

                if (preg_match('/^(-|\*)\s+(.+)$/', $trimmed, $matches)) {
                    if (!$in_list || $list_type !== 'ul') {

                        if ($in_list && $list_type === 'ol') {
                            $formatted_lines[] = '</ol>';
                        }
                        $in_list = true;
                        $list_type = 'ul';
                        $formatted_lines[] = '<ul>';
                    }
                    $formatted_lines[] = '<li>' . esc_html($matches[2]) . '</li>';
                }

                elseif (preg_match('/^(\d+)[\.\)]\s+(.+)$/', $trimmed, $matches)) {
                    if (!$in_list || $list_type !== 'ol') {

                        if ($in_list && $list_type === 'ul') {
                            $formatted_lines[] = '</ul>';
                        }
                        $in_list = true;
                        $list_type = 'ol';
                        $formatted_lines[] = '<ol>';
                    }
                    $formatted_lines[] = '<li>' . esc_html($matches[2]) . '</li>';
                }

                else {

                    if ($in_list) {
                        $in_list = false;
                        $formatted_lines[] = $list_type === 'ul' ? '</ul>' : '</ol>';
                        $list_type = '';
                    }
                    

                    if (preg_match('/^([A-Za-z0-9\s]+):$/', $trimmed, $matches)) {
                        $formatted_lines[] = '<h4>' . esc_html($matches[1]) . '</h4>';
                    } else {

                        $formatted_lines[] = '<p>' . esc_html($trimmed) . '</p>';
                    }
                }
            } elseif (empty($trimmed) && !empty($line)) {

                $formatted_lines[] = '<br>';
            }
        }
        

        if ($in_list) {
            $formatted_lines[] = $list_type === 'ul' ? '</ul>' : '</ol>';
        }
        

        return wp_kses_post(implode("\n", $formatted_lines));
    }
    
    /**
     * Ürün değişkenlerini gerçek değerleriyle değiştiren ve uygun formatta sunan fonksiyon
     * 
     * @param string $content Formatlama yapılacak içerik
     * @param array $productData Ürün verilerini içeren dizi
     * @return string Formatlanmış içerik
     */
    public static function formatProductVariables(string $content, array $productData): string {

        $replacements = [];

        $currency = isset($productData['currency']) ? $productData['currency'] : get_woocommerce_currency();

        $possibleVariables = [
            '{NAME}' => $productData['name'] ?? '',
            '{SHORT_DESCRIPTION}' => $productData['short_description'] ?? '',
            '{PRICE}' => isset($productData['price']) && !empty($productData['price']) ?
                $productData['price'] . " " . $currency : '',
            '{REGULAR_PRICE}' => isset($productData['regular_price']) && !empty($productData['regular_price']) ?
                $productData['regular_price'] . " " . $currency : '',
            '{SALE_PRICE}' => isset($productData['sale_price']) && !empty($productData['sale_price']) ?
                $productData['sale_price'] . " " . $currency : '',
            '{CATEGORIES}' => $productData['categories'] ?? '',
            '{TAGS}' => $productData['tags'] ?? '',
            '{SKU}' => $productData['sku'] ?? '',
            '{ATTRIBUTES}' => $productData['attributes'] ?? '',
        ];

        $safeVariables = VariableConverter::convertVariables($possibleVariables);

        foreach ($safeVariables as $placeholder => $value) {
            if (!empty($value)) {
                $replacements[$placeholder] = $value;
            }
        }

        if (isset($productData['attributes']) && is_array($productData['attributes'])) {
            foreach ($productData['attributes'] as $attrName => $attrValue) {

                $safeValue = VariableConverter::toString($attrValue);
                if (!empty($safeValue)) {
                    $placeholder = '{' . strtoupper($attrName) . '}';
                    $replacements[$placeholder] = $safeValue;
                }
            }
        }
        

        $formattedContent = self::formatVariables($content, $replacements);
        

        preg_match_all('/{([A-Z0-9_]+)}/', $formattedContent, $remainingMatches);
        if (!empty($remainingMatches[0])) {
            foreach ($remainingMatches[0] as $placeholder) {

                $formattedContent = preg_replace('/^\s*' . preg_quote($placeholder, '/') . '\s*$/m', '', $formattedContent);
                $formattedContent = preg_replace('/\n\s*' . preg_quote($placeholder, '/') . '\s*\n/', "\n", $formattedContent);
            }
        }
        

        $formattedContent = preg_replace('/\n{3,}/', "\n\n", $formattedContent);
        
        return self::cleanContent($formattedContent);
    }
} 