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

/**
 * Handles scheduled cleanup of old data.
 *
 * - Sessions + events older than retention_days
 * - Visitor/analytics tables older than retention_days
 * - Stores last cleanup timestamp in wp_options
 */
class VLENS_Cron {

    const HOOK = 'vlens_daily_cleanup';

    /**
     * Schedule the daily cleanup event if not already scheduled.
     */
    public static function schedule() {
        if ( ! wp_next_scheduled( self::HOOK ) ) {
            wp_schedule_event( time(), 'daily', self::HOOK );
        }
    }

    /**
     * Remove the scheduled event (on deactivation).
     */
    public static function unschedule() {
        $timestamp = wp_next_scheduled( self::HOOK );
        if ( $timestamp ) {
            wp_unschedule_event( $timestamp, self::HOOK );
        }
    }

    /**
     * Register the cron callback.
     */
    public static function init() {
        add_action( self::HOOK, [ __CLASS__, 'run_cleanup' ] );
    }

    /**
     * Run the full daily cleanup.
     */
    public static function run_cleanup() {
        global $wpdb;

        $settings       = VLENS_Settings::get_all();
        $retention_days = max( 1, (int) $settings['retention_days'] );
        $now            = current_time( 'timestamp' );
        $cutoff         = gmdate( 'Y-m-d H:i:s', strtotime( "-{$retention_days} days", $now ) );
        $cutoff_date    = gmdate( 'Y-m-d', strtotime( "-{$retention_days} days", $now ) );

        // 1. Delete old session events (for sessions older than retention)
        $t_sessions = VLENS_Helpers::table( 'sessions' );
        $t_events   = VLENS_Helpers::table( 'session_events' );

        $wpdb->query( $wpdb->prepare(
            "DELETE e FROM %i e
             INNER JOIN %i s ON e.session_id = s.id
             WHERE s.started_at < %s",
            $t_events, $t_sessions, $cutoff
        ) );

        // 2. Delete old sessions
        $wpdb->query( $wpdb->prepare(
            "DELETE FROM %i WHERE started_at < %s",
            $t_sessions, $cutoff
        ) );

        // 3. Delete old visitor/analytics data
        self::cleanup_analytics( $cutoff_date );

        // 4. Clean up stale online records (older than 10 minutes)
        $t_online = VLENS_Helpers::table( 'online' );
        $wpdb->query( $wpdb->prepare(
            "DELETE FROM %i WHERE last_active < %s",
            $t_online, gmdate( 'Y-m-d H:i:s', strtotime( '-10 minutes' ) )
        ) );

        // Record last cleanup time
        update_option( 'vlens_last_cleanup', current_time( 'mysql' ), false );
    }

    /**
     * Delete old rows from visitor/analytics aggregate tables.
     */
    private static function cleanup_analytics( string $cutoff_date ) {
        global $wpdb;

        // Core tables — column names are literals, no variable interpolation.
        $t_visitors      = VLENS_Helpers::table( 'visitors' );
        $t_visits        = VLENS_Helpers::table( 'visits' );
        $t_daily_summary = VLENS_Helpers::table( 'daily_summary' );
        $t_countries     = VLENS_Helpers::table( 'countries' );
        $t_browsers      = VLENS_Helpers::table( 'browsers' );
        $t_platforms     = VLENS_Helpers::table( 'platforms' );
        $t_referrers     = VLENS_Helpers::table( 'referrers' );
        $t_search_engines = VLENS_Helpers::table( 'search_engines' );

        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE visit_date < %s", $t_visitors, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE visited_at < %s", $t_visits, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s",       $t_daily_summary, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s",       $t_countries, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s",       $t_browsers, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s",       $t_platforms, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s",       $t_referrers, $cutoff_date ) );
        $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s",       $t_search_engines, $cutoff_date ) );

        // Allow premium to extend cleanup.
        // Each entry: 'table_name' => 'date_col' where date_col must be one of the allowed literals.
        $extra_tables = apply_filters( 'vlens_cron_cleanup', [] );

        $allowed_cols = [ 'visit_date', 'visited_at', 'date', 'created_at', 'started_at' ];

        foreach ( $extra_tables as $name => $date_col ) {
            if ( ! in_array( $date_col, $allowed_cols, true ) ) {
                continue;
            }
            $tbl = VLENS_Helpers::table( $name );
            // Use a switch to embed the column as a literal — no variable interpolation in SQL.
            switch ( $date_col ) {
                case 'visit_date':
                    $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE visit_date < %s", $tbl, $cutoff_date ) );
                    break;
                case 'visited_at':
                    $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE visited_at < %s", $tbl, $cutoff_date ) );
                    break;
                case 'created_at':
                    $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE created_at < %s", $tbl, $cutoff_date ) );
                    break;
                case 'started_at':
                    $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE started_at < %s", $tbl, $cutoff_date ) );
                    break;
                default: // 'date'
                    $wpdb->query( $wpdb->prepare( "DELETE FROM %i WHERE date < %s", $tbl, $cutoff_date ) );
                    break;
            }
        }
    }
}
