<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) {
    exit;
}

class Fold82SM_Mini_Analytics {

    const META_VIEWS       = '_fold82sm_mini_views';
    const META_LAST_VIEWED = '_fold82sm_mini_last_viewed';

    /**
     * Bootstrap.
     */
    public static function init() {
        // Force table creation
        self::install_table();        
        
        add_action( 'template_redirect', array( __CLASS__, 'maybe_track_view' ), 20 );
        add_action( 'wp_ajax_fold82sm_get_mini_analytics', array( __CLASS__, 'ajax_get_mini_analytics' ) );

        // Ensure table exists (safe, runs cheap after first time)
        add_action( 'init', array( __CLASS__, 'install_table' ) );
    }

    /**
     * Track views for published singular posts/pages.
     */
    public static function maybe_track_view() {
        // Allow disabling via filter (future-proof)
        if ( ! apply_filters( 'fold82sm_mini_analytics_enabled', true ) ) {
            return;
        }

        if ( is_admin() || wp_doing_ajax() || wp_is_json_request() ) {
            return;
        }

        if ( ! is_singular() ) {
            return;
        }

        $post_id = (int) get_queried_object_id();
        if ( ! $post_id ) {
            return;
        }

        $post = get_post( $post_id );
        if ( ! $post || 'publish' !== $post->post_status ) {
            return;
        }

        // Minimal scope: only posts + pages (can be extended via filter)
        $allowed_types = apply_filters( 'fold82sm_mini_analytics_allowed_post_types', array( 'post', 'page' ) );
        if ( ! in_array( $post->post_type, $allowed_types, true ) ) {
            return;
        }

        // Exclude only Admin/Editor-like roles (as requested)
        $skip_admin_editor = apply_filters( 'fold82sm_mini_analytics_skip_admin_editor', true );
        if ( $skip_admin_editor && is_user_logged_in() ) {
            $user = wp_get_current_user();
            if ( $user && ( user_can( $user, 'manage_options' ) || user_can( $user, 'edit_others_posts' ) ) ) {
                return;
            }
        }

        self::increment_views( $post_id );
    }

    /**
     * Create daily analytics table.
     *
     * @return void
     */
    public static function install_table() {
        global $wpdb;

        $table = $wpdb->prefix . 'folderra_mini_analytics_daily';
        $charset_collate = $wpdb->get_charset_collate();

        require_once ABSPATH . 'wp-admin/includes/upgrade.php';

        // Verifica se la tabella esiste già
        if ($wpdb->get_var("SHOW TABLES LIKE '{$table}'") != $table) {
            $sql = "CREATE TABLE {$table} (
                id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT,
                post_id BIGINT(20) UNSIGNED NOT NULL,
                day DATE NOT NULL,
                views BIGINT(20) UNSIGNED NOT NULL DEFAULT 0,
                PRIMARY KEY  (id),
                UNIQUE KEY post_day (post_id, day),
                KEY day (day),
                KEY post_id (post_id)
            ) {$charset_collate};";

            dbDelta( $sql );
        }
    }

    /**
     * Increment views: lifetime meta + daily table.
     *
     * @param int $post_id Post ID.
     * @return void
     */
    private static function increment_views( $post_id ) {
        // Lifetime counter (kept for backward compatibility)
        $views = (int) get_post_meta( $post_id, self::META_VIEWS, true );
        $views++;
        update_post_meta( $post_id, self::META_VIEWS, $views );
        update_post_meta( $post_id, self::META_LAST_VIEWED, time() );

        // Daily aggregate
        global $wpdb;
        $table = $wpdb->prefix . 'folderra_mini_analytics_daily';

        $day = gmdate( 'Y-m-d', current_time( 'timestamp' ) );

        // Insert-or-update atomic increment
        $wpdb->query(
            $wpdb->prepare(
                "INSERT INTO {$table} (post_id, day, views)
                 VALUES (%d, %s, 1)
                 ON DUPLICATE KEY UPDATE views = views + 1",
                $post_id,
                $day
            )
        );
    }

    /**
 * AJAX: return top posts/pages by views for dashboard.
 */
public static function ajax_get_mini_analytics() {
    // Verify nonce
    if ( ! check_ajax_referer( 'fold82sm_mini_analytics', 'nonce', false ) ) {
        wp_send_json_error( array( 'message' => 'Nonce verification failed' ), 403 );
    }

    if ( ! current_user_can( 'fold82sm_access' ) ) {
        wp_send_json_error( array( 'message' => 'Not allowed' ), 403 );
    }

    check_ajax_referer( 'fold82sm_mini_analytics', 'nonce' );

    $period = isset( $_POST['period'] ) ? sanitize_key( wp_unslash( $_POST['period'] ) ) : 'today';

    // LIMIT 6 RESULTS
    $limit = 6;

    $data = array(
        'pages' => self::get_top_items_by_period( 'page', $period, $limit ),
        'posts' => self::get_top_items_by_period( 'post', $period, $limit ),
    );

    wp_send_json_success( $data );
}

    /**
     * Query top items by period using daily table.
     *
     * @param string $post_type Post type.
     * @param string $period Period key.
     * @param int    $limit Limit.
     * @return array
     */
    private static function get_top_items_by_period( $post_type, $period, $limit ) {
        global $wpdb;

        $table = $wpdb->prefix . 'folderra_mini_analytics_daily';

        // Whitelist period values
        $allowed_periods = array( 'today', 'week', 'month', 'year', 'all' );
        $period = in_array( $period, $allowed_periods, true ) ? $period : 'today';

        // Build date range (server-local date via CURDATE())
        switch ( $period ) {
            case 'today':
                $where = "d.day = CURDATE()";
                break;
            case 'week':
                $where = "d.day >= (CURDATE() - INTERVAL 6 DAY)";
                break;
            case 'month':
                $where = "d.day >= (CURDATE() - INTERVAL 29 DAY)";
                break;
            case 'year':
                $where = "d.day >= (CURDATE() - INTERVAL 364 DAY)";
                break;
            case 'all':
            default:
                $where = "1=1";
                break;
        }

        $limit = max( 1, min( 20, absint( $limit ) ) );

        $sql = $wpdb->prepare(
            "SELECT p.ID as id, COALESCE(SUM(d.views), 0) as views
             FROM {$wpdb->posts} p
             INNER JOIN {$table} d ON d.post_id = p.ID
             WHERE p.post_type = %s
               AND p.post_status = 'publish'
               AND {$where}
             GROUP BY p.ID
             ORDER BY views DESC, p.ID DESC
             LIMIT %d",
            $post_type,
            $limit
        );

        $rows = $wpdb->get_results( $sql, ARRAY_A );

        $items = array();

        foreach ( $rows as $r ) {
            $pid = absint( $r['id'] );
            if ( ! $pid ) {
                continue;
            }

            $items[] = array(
                'id'       => $pid,
                'title'    => get_the_title( $pid ),
                'views'    => absint( $r['views'] ),
                'edit_url' => get_edit_post_link( $pid, 'raw' ),
                'view_url' => get_permalink( $pid ),
            );
        }

        return $items;
    }

    /**
     * Query top items by views (legacy method, kept for backward compatibility)
     */
    private static function get_top_items( $post_type, $limit ) {
        $q = new WP_Query( array(
            'post_type'              => $post_type,
            'post_status'            => 'publish',
            'posts_per_page'         => $limit,
            'no_found_rows'          => true,
            'ignore_sticky_posts'    => true,
            'meta_key'               => self::META_VIEWS,
            'orderby'                => 'meta_value_num',
            'order'                  => 'DESC',
            'update_post_meta_cache' => true,
            'update_post_term_cache' => false,
            'meta_query'             => array(
                array(
                    'key'     => self::META_VIEWS,
                    'compare' => 'EXISTS',
                ),
            ),
        ) );

        $items = array();

        if ( $q->have_posts() ) {
            foreach ( $q->posts as $p ) {
                $items[] = array(
                    'id'       => (int) $p->ID,
                    'title'    => get_the_title( $p->ID ),
                    'views'    => (int) get_post_meta( $p->ID, self::META_VIEWS, true ),
                    'edit_url' => get_edit_post_link( $p->ID, 'raw' ),
                    'view_url' => get_permalink( $p->ID ),
                );
            }
        }

        return $items;
    }    
}