<?php
/**
 * HTML Compression Class
 * Compresses HTML output by removing unnecessary whitespace
 *
 * @package AIAutoTool
 * @subpackage ExtraConfig
 * @since 1.0.0
 */

if ( ! defined( 'ABSPATH' ) ) exit; // Thoát nếu truy cập trực tiếp

/**
 * HTML Compression class
 */
class Aiautotool_HTML_Compression {
    
    /**
     * Compress CSS
     *
     * @var bool
     */
    protected $compress_css = true;
    
    /**
     * Compress JavaScript
     *
     * @var bool
     */
    protected $compress_js = false; // Disabled by default for safety
    
    /**
     * Add info comment
     *
     * @var bool
     */
    protected $info_comment = true;
    
    /**
     * Remove comments
     *
     * @var bool
     */
    protected $remove_comments = true;
    
    /**
     * Compressed HTML
     *
     * @var string
     */
    protected $html = '';
    
    /**
     * Compress HTML output
     *
     * @param string $html HTML to compress
     * @return string Compressed HTML
     */
    public static function compress($html) {
        if (empty($html) || !is_string($html)) {
            return $html;
        }
        
        $instance = new self();
        return $instance->minify_html($html);
    }
    
    /**
     * Minify HTML
     *
     * @param string $html HTML to minify
     * @return string Minified HTML
     */
    protected function minify_html($html) {
        $pattern = '/<(?<script>script).*?<\/script\s*>|<(?<style>style).*?<\/style\s*>|<!(?<comment>--).*?-->|<(?<tag>[\/\w.:-]*)(?:".*?"|\'.*?\'|[^\'">]+)*>|(?<text>((<[^!\/\w.:-])?[^<]*)+)|/si';
        
        preg_match_all($pattern, $html, $matches, PREG_SET_ORDER);
        
        $overriding = false;
        $raw_tag = false;
        $result = '';
        
        foreach ($matches as $token) {
            $tag = isset($token['tag']) ? strtolower($token['tag']) : null;
            $content = $token[0];
            $strip = true;
            
            if (is_null($tag)) {
                if (!empty($token['script'])) {
                    $strip = $this->compress_js;
                } elseif (!empty($token['style'])) {
                    if ($this->compress_css) {
                        $content = $this->minify_css($content);
                    }
                    $strip = false;
                } elseif ($content === '<!--wp-html-compression no compression-->') {
                    $overriding = !$overriding;
                    continue;
                } elseif ($this->remove_comments) {
                    if (!$overriding && $raw_tag !== 'textarea') {
                        // Keep conditional comments for IE
                        $content = preg_replace('/<!--(?!\s*(?:\[if [^\]]+]|<!|>))(?:(?!-->).)*-->/s', '', $content);
                    }
                }
            } else {
                if ($tag === 'pre' || $tag === 'textarea' || $tag === 'code') {
                    $raw_tag = $tag;
                } elseif ($tag === '/pre' || $tag === '/textarea' || $tag === '/code') {
                    $raw_tag = false;
                } else {
                    if ($raw_tag || $overriding) {
                        $strip = false;
                    } else {
                        $strip = true;
                        // Remove empty attributes (except specific ones)
                        $content = preg_replace('/(\s+)(\w++(?<!\baction|\balt|\bcontent|\bsrc)="")/', '$1', $content);
                        // Remove self-closing tag space
                        $content = str_replace(' />', '/>', $content);
                    }
                }
            }
            
            if ($strip) {
                $content = $this->remove_whitespace($content);
            }
            
            $result .= $content;
        }
        
        if ($this->info_comment) {
            $result .= "\n" . $this->bottom_comment($html, $result);
        }
        
        return $result;
    }
    
    /**
     * Minify CSS content
     *
     * @param string $css CSS content
     * @return string Minified CSS
     */
    protected function minify_css($css) {
        // Remove comments
        $css = preg_replace('!/\*[^*]*\*+([^/][^*]*\*+)*/!', '', $css);
        
        // Remove whitespace
        $css = str_replace(array("\r\n", "\r", "\n", "\t", '  ', '    ', '    '), '', $css);
        
        // Remove spaces around certain characters
        $css = preg_replace('/\s*([\{\}:;,])\s*/', '$1', $css);
        
        return $css;
    }
    
    /**
     * Remove whitespace
     *
     * @param string $str String to clean
     * @return string Cleaned string
     */
    protected function remove_whitespace($str) {
        $str = str_replace("\t", ' ', $str);
        $str = str_replace("\n", '', $str);
        $str = str_replace("\r", '', $str);
        
        // Remove multiple spaces
        while (stristr($str, '  ')) {
            $str = str_replace('  ', ' ', $str);
        }
        
        return $str;
    }
    
    /**
     * Add bottom comment with compression stats
     *
     * @param string $raw        Original HTML
     * @param string $compressed Compressed HTML
     * @return string Comment with stats
     */
    protected function bottom_comment($raw, $compressed) {
        $raw_size = strlen($raw);
        $compressed_size = strlen($compressed);
        $savings = ($raw_size - $compressed_size) / $raw_size * 100;
        $savings = round($savings, 2);
        
        return sprintf(
            '<!-- HTML compressed by AI Auto Tool. Saved %.2f%% (from %d to %d bytes) -->',
            $savings,
            $raw_size,
            $compressed_size
        );
    }
}


