<?php

namespace FleekDash\Controllers\SiteGrowth;

// Load debug helpers
if (!function_exists('fleekdash_log_debug')) {
    require_once FLEEKDASH_PLUGIN_DIR . 'includes/Core/debug-helpers.php';
}

use FleekDash\Services\SiteGrowthMeter\GrowthHelpers;
use WP_REST_Request;
use WP_REST_Response;

/**
 * Events Management Trait for SiteGrowthMeterController
 *
 * Handles all event-related operations (CRUD, tracking, recording)
 *
 * @since 2.2.0 Extracted from SiteGrowthMeterController for better organization
 */
trait EventsManagement
{
    /**
     * Get events
     *
     * @param WP_REST_Request $request Request object
     * @return WP_REST_Response Response object
     * @since 2.2.0 Refactored - Uses GrowthEventsRepository and GrowthDataProcessor
     */
    public function getEvents(WP_REST_Request $request)
    {
        fleekdash_log_debug("DEBUG: getEvents method called");
        try {
            $auth = $this->check_auth_graceful('authenticated');
            $active_only = $request->get_param('active_only') === 'true';

            fleekdash_log_debug("DEBUG: Active only param: " . ($active_only ? 'true' : 'false'));

            // Get events using repository
            $events = $this->repository->getAllEvents($active_only);
            fleekdash_log_debug("DEBUG: Total events from repository: " . count($events));

            // Process events data (add points calculation)
            $events = $this->processor->processEventsData($events);

            return new WP_REST_Response([
                'success' => true,
                'events' => $events,
                'auth_status' => ($auth['authenticated'] ?? false) ? 'authenticated' : 'fallback'
            ], 200);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error getting events: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }

    /**
     * Get single event by ID
     */
    public function getEvent(WP_REST_Request $request)
    {
        try {
            $auth = $this->check_auth_graceful('authenticated');
            $event_id = $request->get_param('id');

            if (!$event_id) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Event ID is required',
                    'auth_status' => 'error'
                ], 400);
            }

            // Get event using repository
            $event = $this->repository->getEventById($event_id);

            if (!$event) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Event not found',
                    'auth_status' => 'error'
                ], 404);
            }

            // Process event data (add points calculation)
            $processed_events = $this->processor->processEventsData([$event]);
            $processed_event = !empty($processed_events) ? $processed_events[0] : $event;

            return new WP_REST_Response([
                'success' => true,
                'event' => $processed_event,
                'auth_status' => ($auth['authenticated'] ?? false) ? 'authenticated' : 'fallback'
            ], 200);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error getting event: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }

    /**
     * Create custom event
     */
    public function createEvent(WP_REST_Request $request)
    {
        try {
            $auth = $this->check_auth_graceful('authenticated');

            if (!($auth['authenticated'] ?? false)) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Authentication required to create event',
                    'auth_status' => 'fallback'
                ], 401);
            }

            $params = $request->get_json_params() ?: [];

            $raw_event_type = $params['event_type'] ?? $request->get_param('event_type');
            $event_type = is_string($raw_event_type) ? \sanitize_key($raw_event_type) : '';

            if ($event_type === '') {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Event type is required',
                    'auth_status' => 'error'
                ], 400);
            }

            // Phase 3: Validate event_type uniqueness (if not custom)
            if ($event_type !== 'custom') {
                $existing_events = \FleekDash\Models\SiteGrowthEvent::where('event_type', $event_type);
                // where() returns an array, get first element if exists
                $existing = !empty($existing_events) ? $existing_events[0] : null;
                if ($existing) {
                    return new WP_REST_Response([
                        'success' => false,
                        'message' => "Event type '{$event_type}' already exists. Each event type can only be created once.",
                        'auth_status' => 'error'
                    ], 400);
                }
            }

            $raw_event_name = $params['event_name'] ?? $request->get_param('event_name');
            $event_name = is_string($raw_event_name) ? trim($raw_event_name) : null;
            if ($event_name !== null && $event_name !== '') {
                $event_name = \sanitize_text_field($event_name);
            } else {
                $event_name = null;
            }

            $tracking_config = $params['tracking_config'] ?? $request->get_param('tracking_config') ?? [];
            if (is_string($tracking_config)) {
                $decoded = json_decode($tracking_config, true);
                // Phase 3: Validate JSON is valid
                if (json_last_error() !== JSON_ERROR_NONE) {
                    return new WP_REST_Response([
                        'success' => false,
                        'message' => 'Invalid JSON in tracking_config: ' . json_last_error_msg(),
                        'auth_status' => 'error'
                    ], 400);
                }
                $tracking_config = is_array($decoded) ? $decoded : [];
            }

            // Phase 3: Ensure tracking_config is always an array
            if (!is_array($tracking_config)) {
                $tracking_config = [];
            }

            $points_override = $params['points_per_event'] ?? $request->get_param('points_override');

            // Phase 3: Validate points_per_event range if provided
            if ($points_override !== null && is_numeric($points_override)) {
                $points_override = (int) $points_override;
                if ($points_override < 1 || $points_override > 1000) {
                    return new WP_REST_Response([
                        'success' => false,
                        'message' => 'points_per_event must be between 1 and 1000',
                        'auth_status' => 'error'
                    ], 400);
                }
            }

            $raw_description = $params['description'] ?? $request->get_param('description');
            $description = is_string($raw_description) && $raw_description !== ''
                ? sanitize_textarea_field($raw_description)
                : null;

            $raw_tracking_method = $params['tracking_method'] ?? $request->get_param('tracking_method') ?? 'manual';
            $tracking_method = is_string($raw_tracking_method) ? \sanitize_key($raw_tracking_method) : 'manual';
            if ($tracking_method === '') {
                $tracking_method = 'manual';
            }

            $is_active = $params['is_active'] ?? $request->get_param('is_active') ?? true;
            $is_active = (bool) $is_active;

            try {
                $event_id = $this->growth_service->createCustomEvent(
                    $event_type,
                    $event_name,
                    $tracking_config,
                    $points_override,
                    $description,
                    $tracking_method,
                    $is_active
                );
            } catch (\InvalidArgumentException $e) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => $e->getMessage(),
                    'auth_status' => 'error'
                ], 400);
            }

            $created_event = \FleekDash\Models\SiteGrowthEvent::find($event_id);

            return new WP_REST_Response([
                'success' => true,
                'event' => $created_event,
                'message' => 'Event created successfully',
                'auth_status' => 'authenticated'
            ], 201);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error creating event: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }

    /**
     * Update event
     */
    public function updateEvent(WP_REST_Request $request)
    {
        try {
            $auth = $this->check_auth_graceful('authenticated');

            if (!($auth['authenticated'] ?? false)) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Authentication required to update event',
                    'auth_status' => 'fallback'
                ], 401);
            }

            $event_id = $request->get_param('id');
            $data = $request->get_json_params();

            $event = \FleekDash\Models\SiteGrowthEvent::find($event_id);
            if (!$event) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Event not found',
                    'auth_status' => 'error'
                ], 404);
            }

            $payload = [];

            if (isset($data['event_type'])) {
                $new_type = \sanitize_key($data['event_type']);
                if ($new_type !== '') {
                    $payload['event_type'] = $new_type;
                }
            }

            if (isset($data['event_name'])) {
                $trimmed = trim((string) $data['event_name']);
                $payload['event_name'] = $trimmed === ''
                    ? GrowthHelpers::buildEventName($event['event_type'])
                    : \sanitize_text_field($trimmed);
            }

            if (isset($data['description'])) {
                $payload['description'] = $data['description'] !== null && $data['description'] !== ''
                    ? sanitize_textarea_field((string) $data['description'])
                    : null;
            }

            if (isset($data['tracking_method'])) {
                $method = \sanitize_key($data['tracking_method']);
                if ($method !== '') {
                    $payload['tracking_method'] = $method;
                }
            }

            if (isset($data['is_active'])) {
                $payload['is_active'] = $data['is_active'] ? 1 : 0;
            }

            $current_cfg = [];
            if (!empty($event['tracking_config'])) {
                $decoded_cfg = is_array($event['tracking_config'])
                    ? $event['tracking_config']
                    : json_decode((string) $event['tracking_config'], true);
                $current_cfg = is_array($decoded_cfg) ? $decoded_cfg : [];
            }

            if (isset($data['points_per_event'])) {
                $points = max(1, min(1000, (int) $data['points_per_event'])); // Validate range (Bug #6)
                $payload['points_per_event'] = $points; // Save directly in column (Bug #2)
                $current_cfg['points_override'] = $points; // Keep in tracking_config for backward compatibility
            }

            if (isset($data['tracking_config'])) {
                $cfg = $data['tracking_config'];
                if (is_string($cfg)) {
                    $decoded = json_decode($cfg, true);
                    $cfg = is_array($decoded) ? $decoded : [];
                }
                if (is_array($cfg)) {
                    $current_cfg = array_merge($current_cfg, $cfg);
                }
            }

            if (!empty($current_cfg)) {
                $payload['tracking_config'] = \wp_json_encode($current_cfg);
            } elseif (array_key_exists('tracking_config', $data)) {
                $payload['tracking_config'] = null;
            }

            if (!empty($payload)) {
                \FleekDash\Models\SiteGrowthEvent::update($event_id, $payload);
            }

            // Update monthly snapshot to reflect point changes or status changes
            $this->growth_service->updateMonthlySnapshot();

            $updated_event = \FleekDash\Models\SiteGrowthEvent::find($event_id);

            return new WP_REST_Response([
                'success' => true,
                'event' => $updated_event,
                'message' => 'Event updated successfully',
                'auth_status' => 'authenticated'
            ], 200);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error updating event: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }

    /**
     * Delete event
     */
    public function deleteEvent(WP_REST_Request $request)
    {
        try {
            $auth = $this->check_auth_graceful('authenticated');

            if (!($auth['authenticated'] ?? false)) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Authentication required to delete event',
                    'auth_status' => 'fallback'
                ], 401);
            }

            $event_id = $request->get_param('id');

            $event = \FleekDash\Models\SiteGrowthEvent::find($event_id);
            if (!$event) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Event not found',
                    'auth_status' => 'error'
                ], 404);
            }

            \FleekDash\Models\SiteGrowthEvent::delete($event_id);

            // Update monthly snapshot to reflect the deletion
            $this->growth_service->updateMonthlySnapshot();

            return new WP_REST_Response([
                'success' => true,
                'message' => 'Event deleted successfully',
                'auth_status' => 'authenticated'
            ], 200);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error deleting event: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }

    /**
     * Track manual event
     */
    public function trackEvent(WP_REST_Request $request)
    {
        try {
            $auth = $this->check_auth_graceful('authenticated');

            if (!($auth['authenticated'] ?? false)) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Authentication required to track event',
                    'auth_status' => 'fallback'
                ], 401);
            }

            $event_type = $request->get_param('event_type');
            $data = $request->get_param('data') ?: [];

            \do_action('fleekdash_track_site_event', $event_type, $data);

            return new WP_REST_Response([
                'success' => true,
                'message' => 'Event tracked successfully',
                'auth_status' => 'authenticated'
            ], 200);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error tracking event: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }

    /**
     * Record event occurrence
     */
    public function recordEvent(WP_REST_Request $request)
    {
        try {
            $auth = $this->check_auth_graceful('authenticated');

            if (!($auth['authenticated'] ?? false)) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Authentication required to record event',
                    'auth_status' => 'fallback'
                ], 401);
            }

            $event_id = $request->get_param('id');
            $custom_points = $request->get_param('custom_points');

            $event = \FleekDash\Models\SiteGrowthEvent::find($event_id);
            if (!$event) {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Event not found',
                    'auth_status' => 'error'
                ], 404);
            }

            // Record the event occurrence
            $event_type = isset($event['event_type']) ? $event['event_type'] : '';

            if ($event_type === '') {
                return new WP_REST_Response([
                    'success' => false,
                    'message' => 'Invalid event type',
                    'auth_status' => 'error'
                ], 400);
            }

            $this->growth_service->trackManualEvent($event_type, [
                'custom_points' => $custom_points,
                'recorded_by' => $auth['user_id']
            ]);

            return new WP_REST_Response([
                'success' => true,
                'message' => 'Event recorded successfully',
                'auth_status' => 'authenticated'
            ], 200);

        } catch (\Exception $e) {
            return new WP_REST_Response([
                'success' => false,
                'message' => 'Error recording event: ' . $e->getMessage(),
                'auth_status' => 'error'
            ], 500);
        }
    }
}
