<?php
if (!defined('ABSPATH')) exit;

class SS_Scanner {

    const TABLE = 'ss_scans';
    const JOB_LIMIT = 10;          // process up to 10 URLs at once
    const MAX_MEMORY_MB = 256;     // soft cap for memory use
    const RETRY_DELAY_SEC = 30;    // retry every 30s instead of 60
    const MAX_RETRIES = 3;

    public static function init() {
        add_filter('cron_schedules', [__CLASS__, 'register_fast_cron']);
        add_action('admin_init', [__CLASS__, 'maybe_schedule']);
        add_action('ss_scanner_run', [__CLASS__, 'run_job']);
        register_activation_hook(SEARCHSHIFTER_PLUGIN_FILE, [__CLASS__, 'install']);
    }

    /** Create DB table */
    public static function install() {
        global $wpdb;
        $table = $wpdb->prefix . self::TABLE;
        $charset = $wpdb->get_charset_collate();

        $sql = "CREATE TABLE IF NOT EXISTS $table (
            id BIGINT UNSIGNED AUTO_INCREMENT PRIMARY KEY,
            url TEXT NOT NULL,
            status VARCHAR(50) DEFAULT 'queued',
            attempts TINYINT DEFAULT 0,
            started_at DATETIME NULL,
            finished_at DATETIME NULL,
            log LONGTEXT NULL
        ) $charset;";

        require_once ABSPATH . 'wp-admin/includes/upgrade.php';
        dbDelta($sql);
    }

    /** Register faster cron (every 10s) */
    public static function register_fast_cron($schedules) {
        if (!isset($schedules['ten_seconds'])) {
            $schedules['ten_seconds'] = [
                'interval' => 10,
                'display'  => __('Every 10 Seconds')
            ];
        }
        return $schedules;
    }

    /** Ensure job schedule exists */
    public static function maybe_schedule() {
        if (!wp_next_scheduled('ss_scanner_run')) {
            wp_schedule_event(time() + 10, 'ten_seconds', 'ss_scanner_run');
        }
    }

    /** Run queued scans */
    public static function run_job() {
        global $wpdb;
        $table = $wpdb->prefix . self::TABLE;

        $running = (int) $wpdb->get_var("SELECT COUNT(*) FROM $table WHERE status='running'");
        if ($running >= self::JOB_LIMIT) return;

        $limit = self::JOB_LIMIT - $running;
        $jobs = $wpdb->get_results("SELECT * FROM $table WHERE status='queued' ORDER BY id ASC LIMIT $limit");
        if (!$jobs) return;

        foreach ($jobs as $job) {
            self::process($job, $table);
        }
    }

    /** Process one scan job */
    protected static function process($job, $table) {
        global $wpdb;
        $wpdb->update($table, [
            'status' => 'running',
            'started_at' => current_time('mysql')
        ], ['id' => $job->id]);

        try {
            $mem = memory_get_usage(true) / 1048576;
            if ($mem > self::MAX_MEMORY_MB) throw new Exception('Memory limit exceeded');

            sleep(1); // simulate small delay

            /** 🔍 Try to find post ID by URL (supports custom CPTs) */
            $post_id = url_to_postid($job->url);
            if (!$post_id) {
                $slug = basename(untrailingslashit(parse_url($job->url, PHP_URL_PATH)));
                $post_id = $wpdb->get_var($wpdb->prepare("
                    SELECT ID FROM {$wpdb->posts}
                    WHERE post_name = %s
                    AND post_status = 'publish'
                    LIMIT 1
                ", $slug));
            }

            /** Default score */
            $score = 60;
            $flags = [];

            if ($post_id) {
                $content = get_post_field('post_content', $post_id);

                // ✅ Check if glossary term tooltips are present
                if (strpos($content, 'ss-glossary-term') !== false) {
                    $score += 10;
                    $flags[] = 'glossary linked';
                }

                // ✅ Check for schema (JSON-LD)
                if (strpos($content, 'application/ld+json') !== false) {
                    $score += 10;
                    $flags[] = 'schema added';
                }

                // ✅ Check for FAQ/Q&A markup
            // ✅ Check for FAQ or Q&A section (HTML heading or keywords)
if (stripos($content, 'Frequently Asked Questions') !== false || stripos($content, 'ss-qa') !== false) {
    $score += 10;
    $flags[] = 'Q&A section found';
}


                // ✅ Check for decent length
                if (str_word_count(strip_tags($content)) > 300) {
                    $score += 10;
                    $flags[] = 'content length OK';
                }
            }

            /** Cap at 100 */
            if ($score > 100) $score = 100;

            /** Preserve old log */
            $existing_log = $wpdb->get_var($wpdb->prepare(
                "SELECT log FROM {$table} WHERE id = %d", $job->id
            ));

            /** Build message */
            $msg = "✅ Scan complete for {$job->url} | Score: {$score}/100";
            if (!empty($flags)) {
                $msg .= " | Found: " . implode(', ', $flags);
            }

            $updated_log = trim(($existing_log ?: '') . "\n" . $msg);

            /** Update record */
            $wpdb->update($table, [
                'status'      => 'done',
                'finished_at' => current_time('mysql'),
                'log'         => $updated_log
            ], ['id' => $job->id]);

        } catch (Exception $e) {
            $attempts = $job->attempts + 1;
            $wpdb->update($table, [
                'status'   => ($attempts >= self::MAX_RETRIES ? 'failed' : 'queued'),
                'attempts' => $attempts,
                'log'      => $e->getMessage()
            ], ['id' => $job->id]);
        }
    }
}

// --- Optional “Force Run” button ---
add_action('admin_post_ss_run_now', function() {
    if (!current_user_can('manage_options')) wp_die('Permission denied');
    do_action('ss_scanner_run');
    wp_safe_redirect(wp_get_referer() ?: admin_url('admin.php?page=searchshifter-visibility-scanner'));
    exit;
});
