<?php
/**
 * Zoho CRM Admin Interface
 *
 * @package HVACCommunityEvents
 */

if (!defined('ABSPATH')) {
    exit;
}

/**
 * Zoho CRM Admin Class
 */
class HVAC_Zoho_Admin {
    
    /**
     * Instance of this class
     * 
     * @var HVAC_Zoho_Admin
     */
    private static $instance = null;
    
    /**
     * Get instance of this class
     * 
     * @return HVAC_Zoho_Admin
     */
    public static function instance() {
        if (null === self::$instance) {
            self::$instance = new self();
        }
        return self::$instance;
    }
    
    /**
     * Initialize the admin interface
     */
    private function __construct() {
        add_action('admin_menu', array($this, 'add_admin_menu'));
        add_action('admin_enqueue_scripts', array($this, 'enqueue_admin_scripts'));
        add_action('wp_ajax_hvac_zoho_test_connection', array($this, 'test_connection'));
        add_action('wp_ajax_hvac_zoho_sync_data', array($this, 'sync_data'));
        add_action('wp_ajax_hvac_zoho_save_credentials', array($this, 'save_credentials'));
        add_action('wp_ajax_hvac_zoho_flush_rewrite_rules', array($this, 'flush_rewrite_rules_ajax'));
        add_action('wp_ajax_hvac_zoho_save_settings', array($this, 'save_settings'));
        add_action('wp_ajax_hvac_zoho_run_scheduled_sync', array($this, 'run_scheduled_sync_now'));
        // Add simple test handler
        add_action('wp_ajax_hvac_zoho_simple_test', array($this, 'simple_test'));
        // Add hash reset handler
        add_action('wp_ajax_hvac_zoho_reset_sync_hashes', array($this, 'reset_sync_hashes'));
        // Add OAuth callback handler - only use one method to prevent duplicates
        add_action('init', array($this, 'add_oauth_rewrite_rule'), 5);
        add_filter('query_vars', array($this, 'add_oauth_query_vars'), 10, 1);
        add_action('template_redirect', array($this, 'handle_oauth_template_redirect'));
        
        // Fallback: Check for OAuth params on init (in case rewrite rules fail and we land on homepage)
        add_action('init', array($this, 'check_for_oauth_params'));
        
        // Ensure rewrite rules are flushed when plugin is activated
        register_activation_hook(HVAC_PLUGIN_FILE, array($this, 'flush_rewrite_rules_on_activation'));
        
        // Initialize scheduled sync if enabled
        $this->init_scheduled_sync();
    }
    
    /**
     * Initialize scheduled sync
     */
    private function init_scheduled_sync() {
        require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-scheduled-sync.php';
        HVAC_Zoho_Scheduled_Sync::instance();
    }
    
    /**
     * Add admin menu
     */
    public function add_admin_menu() {
        add_submenu_page(
            'hvac-community-events',
            'Zoho CRM Sync',
            'Zoho CRM Sync',
            'manage_options',
            'hvac-zoho-sync',
            array($this, 'render_admin_page')
        );
    }
    
    /**
     * Enqueue admin scripts
     */
    public function enqueue_admin_scripts($hook) {
        // Only load on Zoho admin page
        if ($hook !== 'hvac-community-events_page_hvac-zoho-sync') {
            return;
        }

        $site_url = get_site_url();
        $redirect_uri = $site_url . '/oauth/callback';

        // Get OAuth URL if credentials exist
        $oauth_url = '';
        if (!class_exists('HVAC_Secure_Storage')) {
            require_once HVAC_PLUGIN_DIR . 'includes/class-hvac-secure-storage.php';
        }
        $client_id = HVAC_Secure_Storage::get_credential('hvac_zoho_client_id', '');
        $client_secret = HVAC_Secure_Storage::get_credential('hvac_zoho_client_secret', '');

        if (!empty($client_id) && !empty($client_secret)) {
            require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-crm-auth.php';
            $auth = new HVAC_Zoho_CRM_Auth();
            $oauth_url = $auth->get_authorization_url();
        }

        wp_enqueue_script(
            'hvac-zoho-admin',
            HVAC_PLUGIN_URL . 'assets/js/zoho-admin.js',
            array('jquery'),
            HVAC_PLUGIN_VERSION,
            true
        );

        wp_localize_script('hvac-zoho-admin', 'hvacZoho', array(
            'ajaxUrl' => admin_url('admin-ajax.php'),
            'nonce' => wp_create_nonce('hvac_zoho_nonce'),
            'redirectUri' => $redirect_uri,
            'oauthUrl' => $oauth_url
        ));

        wp_enqueue_style(
            'hvac-zoho-admin',
            HVAC_PLUGIN_URL . 'assets/css/zoho-admin.css',
            array(),
            HVAC_PLUGIN_VERSION
        );
    }
    
    /**
     * Render admin page
     */
    public function render_admin_page() {
        $site_url = get_site_url();
        
        // Debug logging

        // Ensure Auth class is loaded for staging detection
        if (!class_exists('HVAC_Zoho_CRM_Auth')) {
            require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-crm-auth.php';
        }
        
        // Use central logic for staging detection
        $is_staging = HVAC_Zoho_CRM_Auth::is_staging_mode();
        
        
        // Load secure storage class
        if (!class_exists('HVAC_Secure_Storage')) {
            require_once HVAC_PLUGIN_DIR . 'includes/class-hvac-secure-storage.php';
        }
        
        // Get stored credentials using secure storage
        $client_id = HVAC_Secure_Storage::get_credential('hvac_zoho_client_id', '');
        $client_secret = HVAC_Secure_Storage::get_credential('hvac_zoho_client_secret', '');
        $stored_refresh_token = HVAC_Secure_Storage::get_credential('hvac_zoho_refresh_token', '');
        $has_credentials = !empty($client_id) && !empty($client_secret);
        // OAuth URL is generated in enqueue_admin_scripts() and passed via wp_localize_script()
        
        // Handle form submission
        if (isset($_GET['credentials_saved'])) {
            echo '<div class="notice notice-success is-dismissible"><p>Zoho CRM credentials saved successfully!</p></div>';
        }
        if (isset($_GET['oauth_success'])) {
            echo '<div class="notice notice-success is-dismissible"><p>OAuth authorization completed successfully!</p></div>';
        }
        if (isset($_GET['oauth_error'])) {
            echo '<div class="notice notice-error is-dismissible"><p>OAuth authorization failed. Please try again.</p></div>';
        }
        
        ?>
        <div class="wrap">
            <h1>Zoho CRM Sync</h1>
            
            <?php if ($is_staging): ?>
                <div class="notice notice-info">
                    <h3>🔧 STAGING MODE ACTIVE</h3>
                    <p><strong>Current site:</strong> <?php echo esc_html($site_url); ?></p>
                    <p>Staging mode is active. Data sync will be simulated only. No actual data will be sent to Zoho CRM.</p>
                    <p>Production sync is only enabled on <strong>upskillhvac.com</strong></p>
                    <p><strong>OAuth Redirect URI:</strong> <?php echo esc_html($site_url . '/oauth/callback'); ?></p>
                    <p><em>Use this redirect URI in your Zoho OAuth app configuration.</em></p>
                </div>
            <?php endif; ?>
            
            <!-- Credentials Configuration Section -->
            <div class="hvac-zoho-credentials">
                <h2>🔑 Zoho CRM Credentials</h2>
                <form id="zoho-credentials-form" method="post">
                    <?php wp_nonce_field('hvac_zoho_credentials', 'hvac_zoho_nonce'); ?>
                    
                    <table class="form-table">
                        <tr>
                            <th scope="row">
                                <label for="zoho_client_id">Client ID</label>
                            </th>
                            <td>
                                <input type="text" id="zoho_client_id" name="zoho_client_id" 
                                       value="<?php echo esc_attr($client_id); ?>" 
                                       class="regular-text" 
                                       placeholder="1000.XXXXXXXXXXXXXXXXXXXXXXXX" />
                                <p class="description">
                                    Your Zoho OAuth Client ID from the Zoho Developer Console.
                                    <a href="https://accounts.zoho.com/developerconsole" target="_blank">Get your Client ID</a>
                                </p>
                            </td>
                        </tr>
                        <tr>
                            <th scope="row">
                                <label for="zoho_client_secret">Client Secret</label>
                            </th>
                            <td>
                                <input type="password" id="zoho_client_secret" name="zoho_client_secret" 
                                       value="<?php echo esc_attr($client_secret); ?>" 
                                       class="regular-text" 
                                       placeholder="Enter your client secret" />
                                <p class="description">
                                    Your Zoho OAuth Client Secret from the Zoho Developer Console.
                                    <button type="button" id="toggle-secret" class="button button-small">Show</button>
                                </p>
                            </td>
                        </tr>
                        <tr>
                            <th scope="row">OAuth Redirect URI</th>
                            <td>
                                <code><?php echo esc_html($site_url . '/oauth/callback'); ?></code>
                                <p class="description">
                                    Use this exact URL in your Zoho OAuth app configuration.
                                    <button type="button" id="copy-redirect-uri" class="button button-small">Copy</button>
                                    <button type="button" id="flush-rewrite-rules" class="button button-small">Flush Rules</button>
                                </p>
                                <?php 
                                // Debug: Check if rewrite rule exists
                                $rewrite_rules = get_option('rewrite_rules');
                                $oauth_rule_exists = isset($rewrite_rules['^oauth/callback/?$']);
                                ?>
                                <p class="description" style="color: <?php echo $oauth_rule_exists ? '#46b450' : '#dc3232'; ?>">
                                    OAuth rewrite rule: <?php echo $oauth_rule_exists ? '✓ Active' : '✗ Missing (click Flush Rules)'; ?>
                                </p>
                            </td>
                        </tr>
                        <tr>
                            <th scope="row">Connection Status</th>
                            <td>
                                <?php if (!$has_credentials): ?>
                                    <span class="dashicons dashicons-dismiss" style="color: #dc3232;"></span>
                                    <span style="color: #dc3232;">No credentials configured</span>
                                <?php elseif (empty($stored_refresh_token)): ?>
                                    <span class="dashicons dashicons-warning" style="color: #ffb900;"></span>
                                    <span style="color: #ffb900;">Credentials set, OAuth authorization required</span>
                                <?php else: ?>
                                    <span class="dashicons dashicons-yes-alt" style="color: #46b450;"></span>
                                    <span style="color: #46b450;">Connected and authorized</span>
                                <?php endif; ?>
                            </td>
                        </tr>
                    </table>
                    
                    <p class="submit">
                        <button type="submit" class="button button-primary" id="save-credentials">
                            Save Credentials
                        </button>
                        <?php if ($has_credentials && empty($stored_refresh_token)): ?>
                            <button type="button" class="button button-secondary" id="start-oauth" style="margin-left: 10px;">
                                🚀 Authorize with Zoho
                            </button>
                        <?php endif; ?>
                        <button type="button" class="button button-secondary" id="diagnostic-test" style="margin-left: 10px;">
                            🏥 Run Diagnostic Test
                        </button>
                    </p>
                </form>
            </div>
            
            <?php if ($has_credentials): ?>
                <div class="hvac-zoho-status">
                    <h2>Connection Test</h2>
                    <p>Test your Zoho CRM connection to ensure everything is working properly.</p>
                    
                    <?php if (empty($stored_refresh_token)): ?>
                        <div class="notice notice-warning">
                            <p><strong>⚠️ OAuth Authorization Required</strong></p>
                            <p>You have saved credentials but need to authorize the application with Zoho CRM.</p>
                            <p>Click "Authorize with Zoho" above to complete the setup.</p>
                        </div>
                    <?php else: ?>
                        <button class="button button-primary" id="test-connection">Test Connection</button>
                        <div id="connection-status"></div>
                    <?php endif; ?>
                </div>
                
                <div class="hvac-zoho-sync">
                    <h2>Data Sync</h2>

                    <div class="sync-maintenance" style="margin-bottom: 20px; padding: 12px 15px; background: #fff8e5; border-left: 4px solid #ffb900;">
                        <p style="margin: 0 0 8px 0;"><strong>Sync Maintenance</strong></p>
                        <p style="margin: 0 0 8px 0; font-size: 13px;">If records aren't syncing (e.g. after a failed sync or configuration change), reset sync hashes to force all records to re-sync on the next run.</p>
                        <button class="button" id="reset-sync-hashes">Force Full Re-sync (Reset Hashes)</button>
                        <span id="reset-hashes-status" style="margin-left: 10px;"></span>
                    </div>

                    <div class="sync-section">
                        <h3>Events → Campaigns</h3>
                        <p>Sync events from The Events Calendar to Zoho CRM Campaigns</p>
                        <button class="button sync-button" data-type="events">Sync Events</button>
                        <div class="sync-status" id="events-status"></div>
                    </div>

                    <div class="sync-section">
                        <h3>Trainers → Contacts</h3>
                        <p>Sync trainers (hvac_trainer, hvac_master_trainer) to Zoho CRM Contacts</p>
                        <button class="button sync-button" data-type="users">Sync Trainers</button>
                        <div class="sync-status" id="users-status"></div>
                    </div>

                    <div class="sync-section">
                        <h3>Ticket Attendees → Contacts + Campaign Members</h3>
                        <p>Sync Event Tickets attendees to Zoho CRM Contacts and link them to Campaigns</p>
                        <button class="button sync-button" data-type="attendees">Sync Attendees</button>
                        <div class="sync-status" id="attendees-status"></div>
                    </div>

                    <div class="sync-section">
                        <h3>RSVPs → Leads + Campaign Members</h3>
                        <p>Sync RSVP responses to Zoho CRM Leads and link them to Campaigns</p>
                        <button class="button sync-button" data-type="rsvps">Sync RSVPs</button>
                        <div class="sync-status" id="rsvps-status"></div>
                    </div>

                    <div class="sync-section">
                        <h3>Ticket Orders → Invoices</h3>
                        <p>Sync Event Tickets orders (Tickets Commerce) to Zoho CRM Invoices</p>
                        <button class="button sync-button" data-type="purchases">Sync Orders</button>
                        <div class="sync-status" id="purchases-status"></div>
                    </div>
                </div>
                
                <div class="hvac-zoho-settings">
                    <h2>Scheduled Sync Settings</h2>
                    <?php
                    // Get scheduled sync status
                    require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-scheduled-sync.php';
                    $scheduled_sync = HVAC_Zoho_Scheduled_Sync::instance();
                    $sync_status = $scheduled_sync->get_status();
                    $current_frequency = get_option('hvac_zoho_sync_frequency', 'every_5_minutes');
                    ?>
                    <form id="zoho-settings-form">
                        <table class="form-table">
                            <tr>
                                <th scope="row">Enable Scheduled Sync</th>
                                <td>
                                    <label>
                                        <input type="checkbox" name="auto_sync" value="1" <?php checked(get_option('hvac_zoho_auto_sync'), '1'); ?>>
                                        Automatically sync new/modified records to Zoho CRM
                                    </label>
                                    <p class="description">When enabled, a background process will sync changes on the selected interval.</p>
                                </td>
                            </tr>
                            <tr>
                                <th scope="row">Sync Interval</th>
                                <td>
                                    <select name="sync_frequency">
                                        <option value="every_5_minutes" <?php selected($current_frequency, 'every_5_minutes'); ?>>Every 5 minutes</option>
                                        <option value="every_15_minutes" <?php selected($current_frequency, 'every_15_minutes'); ?>>Every 15 minutes</option>
                                        <option value="every_30_minutes" <?php selected($current_frequency, 'every_30_minutes'); ?>>Every 30 minutes</option>
                                        <option value="hourly" <?php selected($current_frequency, 'hourly'); ?>>Hourly</option>
                                        <option value="every_6_hours" <?php selected($current_frequency, 'every_6_hours'); ?>>Every 6 hours</option>
                                        <option value="daily" <?php selected($current_frequency, 'daily'); ?>>Daily</option>
                                    </select>
                                    <p class="description">How often to check for and sync new/modified records.</p>
                                </td>
                            </tr>
                            <tr>
                                <th scope="row">Sync Status</th>
                                <td>
                                    <p>
                                        <strong>Status:</strong> 
                                        <?php if ($sync_status['is_scheduled']): ?>
                                            <span style="color: #46b450;">✓ Scheduled</span>
                                        <?php else: ?>
                                            <span style="color: #dc3232;">✗ Not Scheduled</span>
                                        <?php endif; ?>
                                    </p>
                                    <p>
                                        <strong>Last Sync:</strong> 
                                        <?php echo esc_html($sync_status['last_sync_formatted']); ?>
                                    </p>
                                    <?php if ($sync_status['is_scheduled']): ?>
                                    <p>
                                        <strong>Next Sync:</strong> 
                                        <?php echo esc_html($sync_status['next_sync_formatted']); ?>
                                    </p>
                                    <?php endif; ?>
                                    <?php if ($sync_status['last_result']): ?>
                                    <p>
                                        <strong>Last Result:</strong> 
                                        <?php 
                                        $last = $sync_status['last_result'];
                                        echo esc_html(sprintf('%d synced, %d failed', $last['total_synced'] ?? 0, $last['total_failed'] ?? 0));
                                        ?>
                                    </p>
                                    <?php endif; ?>
                                </td>
                            </tr>
                        </table>
                        
                        <p class="submit">
                            <button type="submit" class="button button-primary">Save Settings</button>
                            <button type="button" class="button button-secondary" id="run-scheduled-sync-now" style="margin-left: 10px;">
                                🔄 Run Sync Now
                            </button>
                        </p>
                    </form>
                    <div id="scheduled-sync-status"></div>
                </div>
            <?php endif; ?>
        </div>
        <?php
        // Note: All JavaScript functionality moved to assets/js/zoho-admin.js
        // Data is passed via wp_localize_script() in enqueue_admin_scripts()
    }
    
    /**
     * Simple test handler to isolate issues
     */
    public function simple_test() {
        // Check permissions
        if (!current_user_can('manage_options')) {
            wp_send_json_error(array('message' => 'Unauthorized access'));
            return;
        }

        $payload_status = 'No payload received';
        if (!empty($_POST['test_payload'])) {
            $payload_status = 'Payload received (' . strlen($_POST['test_payload']) . ' chars)';
        }

        wp_send_json_success(array(
            'message' => 'Simple test works!', 
            'server_time' => date('Y-m-d H:i:s'),
            'payload_status' => $payload_status,
            'request_method' => $_SERVER['REQUEST_METHOD']
        ));
    }
    
    /**
     * Save Zoho CRM credentials
     */
    public function save_credentials() {
        if (!current_user_can('manage_options')) {
            wp_send_json_error(array('message' => 'Unauthorized access'));
            return;
        }
        
        if (!check_ajax_referer('hvac_zoho_credentials', 'nonce', false)) {
            wp_send_json_error(array('message' => 'Invalid nonce'));
            return;
        }
        
        $client_id = sanitize_text_field($_POST['zoho_client_id']);
        $client_secret = sanitize_text_field($_POST['zoho_client_secret']);
        
        if (empty($client_id) || empty($client_secret)) {
            wp_send_json_error(array('message' => 'Client ID and Client Secret are required'));
            return;
        }
        
        // Validate Client ID format (should start with "1000.")
        if (!preg_match('/^1000\.[A-Za-z0-9]+$/', $client_id)) {
            wp_send_json_error(array('message' => 'Invalid Client ID format. Should start with "1000."'));
            return;
        }
        
        // Load secure storage class
        if (!class_exists('HVAC_Secure_Storage')) {
            require_once HVAC_PLUGIN_DIR . 'includes/class-hvac-secure-storage.php';
        }
        
        // Save credentials using secure storage
        if (!HVAC_Secure_Storage::store_credential('hvac_zoho_client_id', $client_id) ||
            !HVAC_Secure_Storage::store_credential('hvac_zoho_client_secret', $client_secret)) {
            wp_send_json_error(array('message' => 'Failed to securely store credentials'));
            return;
        }
        
        // Clear any existing refresh token since credentials changed
        HVAC_Secure_Storage::store_credential('hvac_zoho_refresh_token', '');
        
        wp_send_json_success(array(
            'message' => 'Credentials saved successfully',
            'client_id_preview' => substr($client_id, 0, 10) . '...'
        ));
    }
    
    /**
     * Flush rewrite rules via AJAX
     */
    public function flush_rewrite_rules_ajax() {
        if (!current_user_can('manage_options')) {
            wp_send_json_error(array('message' => 'Unauthorized access'));
            return;
        }
        
        // Clear any cached rules first
        wp_cache_delete('rewrite_rules', 'options');
        
        // Add OAuth rewrite rules multiple ways
        add_rewrite_rule('^oauth/callback/?$', 'index.php?hvac_oauth_callback=1', 'top');
        add_rewrite_rule('oauth/callback/?$', 'index.php?hvac_oauth_callback=1', 'top');
        
        // Force hard flush
        flush_rewrite_rules(true);
        
        // Clear cache again
        wp_cache_delete('rewrite_rules', 'options');
        
        // Add rules again and soft flush
        $this->add_oauth_rewrite_rule();
        flush_rewrite_rules(false);
        
        // Force WordPress to regenerate rules
        delete_option('rewrite_rules');
        wp_cache_delete('rewrite_rules', 'options');
        $wp_rewrite = $GLOBALS['wp_rewrite'];
        $wp_rewrite->flush_rules(true);
        
        // Verify the rule exists after flush
        $rewrite_rules = get_option('rewrite_rules', array());
        $oauth_rule_exists = isset($rewrite_rules['^oauth/callback/?$']) || isset($rewrite_rules['oauth/callback/?$']);
        
        // Log for debugging
        
        wp_send_json_success(array(
            'message' => 'Rewrite rules flushed successfully',
            'oauth_rule_exists' => $oauth_rule_exists,
            'total_rules' => count($rewrite_rules),
            'rules_sample' => array_slice(array_keys($rewrite_rules), 0, 5)
        ));
    }
    
    /**
     * Flush rewrite rules on plugin activation
     */
    public function flush_rewrite_rules_on_activation() {
        $this->add_oauth_rewrite_rule();
        flush_rewrite_rules();
    }
    
    /**
     * Add OAuth query vars
     */
    public function add_oauth_query_vars($vars) {
        // Only add if not already present to avoid duplicates
        if (!in_array('hvac_oauth_callback', $vars)) {
            $vars[] = 'hvac_oauth_callback';
        }
        return $vars;
    }
    
    /**
     * Add OAuth query vars to public query vars
     */
    public function add_public_query_vars() {
        global $wp;
        // Check if already added to avoid duplicates
        if (!in_array('hvac_oauth_callback', $wp->public_query_vars)) {
            $wp->add_query_var('hvac_oauth_callback');
        }
    }
    
    public function parse_oauth_request($wp) {

        // Check if this is an OAuth callback request
        if (preg_match('#^/oauth/callback/?#', $_SERVER['REQUEST_URI'])) {

            // Check if we have the code parameter
            if (isset($_GET['code'])) {
                $this->process_oauth_callback();
                exit;
            } else {

                wp_die('OAuth callback missing authorization code');
            }
        }
    }

    /**
     * Manual Router for OAuth Callback
     * 
     * Catches the request on 'init' before WordPress internal routing can 404 it.
     * This is a robust fallback for when rewrite rules fail or haven't flushed.
     */
    public function check_for_oauth_params() {
        // Check if we are at the oauth callback URL path
        $path = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
        
        // Check strict path match or if regex matches
        if (strpos($path, '/oauth/callback') !== false) {
            
            // We are at the right URL. Do we have the code?
            if (isset($_GET['code'])) {
                
                // We have a code.
                // We MUST process this, otherwise WP will display a 404.
                // Even if state matches or not, we should handle it here.
                // The process_oauth_callback method handles validation.
                
                $this->process_oauth_callback();
                // process_oauth_callback exits, so we won't continue to 404.
            }
        }
    }
    
    /**
     * Add OAuth callback rewrite rule
     */
    public function add_oauth_rewrite_rule() {
        add_rewrite_rule('^oauth/callback/?$', 'index.php?hvac_oauth_callback=1', 'top');
        
        // Also add alternative rule patterns
        add_rewrite_rule('oauth/callback/?$', 'index.php?hvac_oauth_callback=1', 'top');
        
        // Force flush if the rule doesn't exist
        $rewrite_rules = get_option('rewrite_rules');
        if (!$rewrite_rules || !isset($rewrite_rules['^oauth/callback/?$'])) {
            // Set a flag to flush rules on next page load
            update_option('hvac_oauth_rules_need_flush', true);
            
            // Also try to flush immediately if we're in admin
            if (is_admin()) {
                flush_rewrite_rules(false);
            }
        }
        
        // Check if we need to flush based on flag
        if (get_option('hvac_oauth_rules_need_flush')) {
            flush_rewrite_rules(false);
            delete_option('hvac_oauth_rules_need_flush');
        }
    }
    
    /**
     * Handle OAuth template redirect
     */
    public function handle_oauth_template_redirect() {
        if (get_query_var('hvac_oauth_callback')) {
            $this->process_oauth_callback();
        }
    }
    
    /**
     * Process OAuth callback from Zoho
     */
    public function process_oauth_callback() {
        if (!isset($_GET['code'])) {
            wp_die('OAuth callback missing authorization code');
        }

        // Validate state parameter for CSRF protection
        if (!isset($_GET['state'])) {
            wp_die('OAuth callback missing state parameter. Possible CSRF attack.');
        }

        // Load secure storage for credential handling
        if (!class_exists('HVAC_Secure_Storage')) {
            require_once HVAC_PLUGIN_DIR . 'includes/class-hvac-secure-storage.php';
        }

        require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-crm-auth.php';
        $auth = new HVAC_Zoho_CRM_Auth();

        if (!$auth->validate_oauth_state(sanitize_text_field($_GET['state']))) {
            wp_die('OAuth state validation failed. Please try the authorization again.');
        }

        // Get credentials using secure storage (credentials are stored encrypted)
        if (!class_exists('HVAC_Secure_Storage')) {
            require_once HVAC_PLUGIN_DIR . 'includes/class-hvac-secure-storage.php';
        }
        $client_id = HVAC_Secure_Storage::get_credential('hvac_zoho_client_id', '');
        $client_secret = HVAC_Secure_Storage::get_credential('hvac_zoho_client_secret', '');
        
        if (empty($client_id) || empty($client_secret)) {
            wp_die('OAuth callback error: Missing client credentials. Please configure your Zoho CRM credentials first.');
        }
        
        // Exchange authorization code for tokens
        $token_url = 'https://accounts.zoho.com/oauth/v2/token';
        $redirect_uri = get_site_url() . '/oauth/callback';
        
        $token_params = array(
            'grant_type' => 'authorization_code',
            'client_id' => $client_id,
            'client_secret' => $client_secret,
            'redirect_uri' => $redirect_uri,
            'code' => $_GET['code']
        );
        
        $response = wp_remote_post($token_url, array(
            'body' => $token_params,
            'timeout' => 30
        ));
        
        if (is_wp_error($response)) {
            wp_redirect(admin_url('admin.php?page=hvac-zoho-sync&oauth_error=1&error_msg=' . urlencode($response->get_error_message())));
            exit;
        }
        
        $body = wp_remote_retrieve_body($response);
        $token_data = json_decode($body, true);

        // Check for errors in response
        if (isset($token_data['error'])) {
            wp_redirect(admin_url('admin.php?page=hvac-zoho-sync&oauth_error=1&error_msg=' . urlencode($token_data['error'])));
            exit;
        }
        
        if (!isset($token_data['access_token'])) {

            wp_redirect(admin_url('admin.php?page=hvac-zoho-sync&oauth_error=1&error_msg=' . urlencode('No access token received')));
            exit;
        }
        
        // Save tokens using secure storage
        HVAC_Secure_Storage::store_credential('hvac_zoho_access_token', $token_data['access_token']);
        update_option('hvac_zoho_token_expires', time() + ($token_data['expires_in'] ?? 3600));

        // Refresh token might not be returned on subsequent authorizations
        if (isset($token_data['refresh_token']) && !empty($token_data['refresh_token'])) {
            HVAC_Secure_Storage::store_credential('hvac_zoho_refresh_token', $token_data['refresh_token']);
        } else {
            $existing_refresh = HVAC_Secure_Storage::get_credential('hvac_zoho_refresh_token', '');
            if (empty($existing_refresh)) {
                // This is critical - we need a refresh token for long-term access
                // Store a warning but still complete the flow
                update_option('hvac_zoho_missing_refresh_token', true);
            }
        }

        // Success - redirect to admin page with success message
        wp_redirect(admin_url('admin.php?page=hvac-zoho-sync&oauth_success=1'));
        exit;
    }
    
    /**
     * Handle OAuth callback from Zoho (legacy method)
     */
    public function handle_oauth_callback() {
        // This method is kept for backwards compatibility
        // The main handling is now done in template_redirect
        return;
    }
    
    /**
     * Test Zoho connection
     */
    public function test_connection() {
        
        try {
            check_ajax_referer('hvac_zoho_nonce', 'nonce');
            
            if (!current_user_can('manage_options')) {
                wp_send_json_error(array('message' => 'Unauthorized access'));
                return;
            }

            // Get credentials using secure storage (credentials are stored encrypted)
            if (!class_exists('HVAC_Secure_Storage')) {
                require_once HVAC_PLUGIN_DIR . 'includes/class-hvac-secure-storage.php';
            }
            $client_id = HVAC_Secure_Storage::get_credential('hvac_zoho_client_id', '');
            $client_secret = HVAC_Secure_Storage::get_credential('hvac_zoho_client_secret', '');
            
            // Check configuration before attempting connection
            if (empty($client_id)) {
                wp_send_json_error(array(
                    'message' => 'Configuration Error',
                    'error' => 'Client ID is not configured',
                    'details' => 'Please enter your Zoho CRM Client ID in the form above',
                    'help' => 'Get your Client ID from the Zoho Developer Console'
                ));
                return;
            }
            
            if (empty($client_secret)) {
                wp_send_json_error(array(
                    'message' => 'Configuration Error',
                    'error' => 'Client Secret is not configured',
                    'details' => 'Please enter your Zoho CRM Client Secret in the form above',
                    'help' => 'Get your Client Secret from the Zoho Developer Console'
                ));
                return;
            }
            
            // Check if we have stored refresh token from previous OAuth
            $stored_refresh_token = HVAC_Secure_Storage::get_credential('hvac_zoho_refresh_token', '');
            
            if (empty($stored_refresh_token)) {
                
                $site_url = get_site_url();
                $redirect_uri = $site_url . '/oauth/callback';
                $scopes = 'ZohoCRM.settings.ALL,ZohoCRM.modules.ALL,ZohoCRM.users.ALL,ZohoCRM.org.ALL,ZohoCRM.bulk.READ';
                $auth_url = 'https://accounts.zoho.com/oauth/v2/auth?' . http_build_query(array(
                    'scope' => $scopes,
                    'client_id' => $client_id,
                    'response_type' => 'code',
                    'access_type' => 'offline',
                    'redirect_uri' => $redirect_uri,
                    'prompt' => 'consent'
                ));
                
                wp_send_json_error(array(
                    'message' => 'OAuth Authorization Required',
                    'error' => 'No stored refresh token found',
                    'details' => 'You have valid credentials but need to complete OAuth authorization to get a fresh token',
                    'help' => 'Click the "Authorize with Zoho" button above to complete setup',
                    'next_steps' => array(
                        '1. Click the "Authorize with Zoho" button above',
                        '2. Sign in to your Zoho account', 
                        '3. Grant permissions to the application',
                        '4. You will be redirected back and the refresh token will be saved automatically'
                    ),
                    'auth_url' => $auth_url,
                    'credentials_status' => array(
                        'client_id' => substr($client_id, 0, 10) . '...',
                        'client_secret_exists' => true,
                        'refresh_token_exists' => false
                    )
                ));
                return;
            }
            
            // We have a refresh token - test the actual API connection
            require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-crm-auth.php';
            $auth = new HVAC_Zoho_CRM_Auth();
            
            
            // Test API call
            $response = $auth->make_api_request('/settings/modules', 'GET');
            
            if (is_wp_error($response)) {
                wp_send_json_error(array(
                    'message' => 'API Connection Failed',
                    'error' => $response->get_error_message(),
                    'details' => 'WordPress HTTP error occurred'
                ));
                return;
            }

            if (isset($response['error'])) {
                
                // Check if it's an invalid token error
                if (strpos($response['error'], 'invalid') !== false || strpos($response['error'], 'expired') !== false) {

                    // Clear the invalid token and trigger OAuth
                    delete_option('hvac_zoho_refresh_token');
                    
                    $auth_url = $auth->get_authorization_url();
                    $site_url = get_site_url();
                    $redirect_uri = $site_url . '/oauth/callback';
                    $scopes = 'ZohoCRM.settings.ALL,ZohoCRM.modules.ALL,ZohoCRM.users.ALL,ZohoCRM.org.ALL,ZohoCRM.bulk.READ';
                    $new_auth_url = 'https://accounts.zoho.com/oauth/v2/auth?' . http_build_query(array(
                        'scope' => $scopes,
                        'client_id' => $client_id,
                        'response_type' => 'code',
                        'access_type' => 'offline',
                        'redirect_uri' => $redirect_uri,
                        'prompt' => 'consent'
                    ));
                    
                    wp_send_json_error(array(
                        'message' => 'OAuth Authorization Required',
                        'error' => 'Refresh token expired or invalid',
                        'details' => 'The stored refresh token is no longer valid. Please re-authorize.',
                        'help' => 'Refresh the page and click "Authorize with Zoho" again',
                        'next_steps' => array(
                            '1. Refresh this page',
                            '2. Click the "Authorize with Zoho" button',
                            '3. Sign in to your Zoho account', 
                            '4. Grant permissions to the application',
                            '5. You will be redirected back and the refresh token will be saved automatically'
                        ),
                        'auth_url' => $new_auth_url,
                        'credentials_status' => array(
                            'client_id' => substr($client_id, 0, 10) . '...',
                            'client_secret_exists' => true,
                            'refresh_token_exists' => false
                        )
                    ));
                    return;
                }
                
                wp_send_json_error(array(
                    'message' => 'Zoho API Error', 
                    'error' => $response['error'],
                    'details' => isset($response['details']) ? $response['details'] : 'No additional details'
                ));
                return;
            }
            
            // Success!
            $mode_info = HVAC_Zoho_CRM_Auth::get_debug_mode_info();
            $response_data = array(
                'message' => 'Connection successful!',
                'modules' => isset($response['modules']) ? count($response['modules']) . ' modules available' : 'API connected',
                'client_id' => substr($client_id, 0, 10) . '...',
                'client_secret_exists' => true,
                'refresh_token_exists' => true,
                'is_staging' => $mode_info['is_staging'],
                'mode_info' => $mode_info,
                'credentials_status' => array(
                    'client_id' => substr($client_id, 0, 10) . '...',
                    'client_secret_exists' => true,
                    'refresh_token_exists' => true,
                    'api_working' => true
                )
            );

            if ($mode_info['is_staging']) {
                $response_data['staging_warning'] = 'WARNING: Staging mode is active. All write operations (sync) are blocked. Hostname: ' . ($mode_info['parsed_host'] ?? 'unknown');
            }

            wp_send_json_success($response_data);
        } catch (Exception $e) {
            $error_response = array(
                'message' => 'Connection test failed due to exception',
                'error' => $e->getMessage(),
            );
            // Only expose file paths in debug mode
            if (defined('WP_DEBUG') && WP_DEBUG) {
                $error_response['file'] = $e->getFile() . ':' . $e->getLine();
            }
            wp_send_json_error($error_response);
        } catch (Error $e) {
            $error_response = array(
                'message' => 'Connection test failed due to PHP error',
                'error' => $e->getMessage(),
            );
            if (defined('WP_DEBUG') && WP_DEBUG) {
                $error_response['file'] = $e->getFile() . ':' . $e->getLine();
            }
            wp_send_json_error($error_response);
        } catch (Throwable $e) {
            $error_response = array(
                'message' => 'Connection test failed due to fatal error',
                'error' => $e->getMessage(),
            );
            if (defined('WP_DEBUG') && WP_DEBUG) {
                $error_response['file'] = $e->getFile() . ':' . $e->getLine();
            }
            wp_send_json_error($error_response);
        }
    }
    
    /**
     * Sync data to Zoho
     */
    public function sync_data() {
        check_ajax_referer('hvac_zoho_nonce', 'nonce');
        
        if (!current_user_can('manage_options')) {
            wp_die('Unauthorized');
        }
        
        $type = sanitize_text_field($_POST['type']);
        $offset = isset($_POST['offset']) ? absint($_POST['offset']) : 0;
        $limit = isset($_POST['limit']) ? absint($_POST['limit']) : 50;
        
        try {
            require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-sync.php';
            $sync = new HVAC_Zoho_Sync();
            
            switch ($type) {
                case 'events':
                    $result = $sync->sync_events($offset, $limit);
                    break;
                case 'users':
                    $result = $sync->sync_users($offset, $limit);
                    break;
                case 'attendees':
                    $result = $sync->sync_attendees($offset, $limit);
                    break;
                case 'rsvps':
                    $result = $sync->sync_rsvps($offset, $limit);
                    break;
                case 'purchases':
                    $result = $sync->sync_purchases($offset, $limit);
                    break;
                default:
                    throw new Exception('Invalid sync type');
            }
            
            wp_send_json_success($result);
        } catch (Exception $e) {
            wp_send_json_error(array(
                'message' => 'Sync failed',
                'error' => $e->getMessage()
            ));
        }
    }

    /**
     * Save scheduled sync settings
     */
    public function save_settings() {
        check_ajax_referer('hvac_zoho_nonce', 'nonce');
        
        if (!current_user_can('manage_options')) {
            wp_send_json_error(array('message' => 'Unauthorized access'));
            return;
        }
        
        $auto_sync = isset($_POST['auto_sync']) && $_POST['auto_sync'] === '1' ? '1' : '0';
        $sync_frequency = sanitize_text_field($_POST['sync_frequency'] ?? 'every_5_minutes');
        
        // Validate frequency value
        $valid_frequencies = array(
            'every_5_minutes',
            'every_15_minutes', 
            'every_30_minutes',
            'hourly',
            'every_6_hours',
            'daily'
        );
        
        if (!in_array($sync_frequency, $valid_frequencies)) {
            $sync_frequency = 'every_5_minutes';
        }
        
        // Save settings
        update_option('hvac_zoho_auto_sync', $auto_sync);
        update_option('hvac_zoho_sync_frequency', $sync_frequency);

        // Get scheduled sync instance and explicitly schedule/unschedule
        // This ensures scheduling works even if option value didn't change
        require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-scheduled-sync.php';
        $scheduled_sync = HVAC_Zoho_Scheduled_Sync::instance();

        if ($auto_sync === '1') {
            $scheduled_sync->schedule_sync($sync_frequency);
        } else {
            $scheduled_sync->unschedule_sync();
        }

        $status = $scheduled_sync->get_status();
        
        wp_send_json_success(array(
            'message' => 'Settings saved successfully',
            'auto_sync' => $auto_sync,
            'sync_frequency' => $sync_frequency,
            'is_scheduled' => $status['is_scheduled'],
            'next_sync' => $status['next_sync_formatted']
        ));
    }
    
    /**
     * Run scheduled sync manually
     */
    public function run_scheduled_sync_now() {
        check_ajax_referer('hvac_zoho_nonce', 'nonce');

        if (!current_user_can('manage_options')) {
            wp_send_json_error(array('message' => 'Unauthorized access'));
            return;
        }

        try {
            require_once HVAC_PLUGIN_DIR . 'includes/zoho/class-zoho-scheduled-sync.php';
            $scheduled_sync = HVAC_Zoho_Scheduled_Sync::instance();

            $result = $scheduled_sync->run_now();

            wp_send_json_success(array(
                'message' => 'Scheduled sync completed',
                'result' => $result
            ));
        } catch (Exception $e) {
            wp_send_json_error(array(
                'message' => 'Sync failed',
                'error' => $e->getMessage()
            ));
        }
    }

    /**
     * Reset all Zoho sync hashes to force a full re-sync
     */
    public function reset_sync_hashes() {
        check_ajax_referer('hvac_zoho_nonce', 'nonce');

        if (!current_user_can('manage_options')) {
            wp_send_json_error(array('message' => 'Unauthorized access'));
            return;
        }

        global $wpdb;

        // Delete all _zoho_sync_hash post meta
        $posts_cleared = $wpdb->query(
            "DELETE FROM {$wpdb->postmeta} WHERE meta_key = '_zoho_sync_hash'"
        );

        // Delete all _zoho_sync_hash user meta
        $users_cleared = $wpdb->query(
            "DELETE FROM {$wpdb->usermeta} WHERE meta_key = '_zoho_sync_hash'"
        );

        // Also clear last sync time so scheduled sync does a full run
        delete_option('hvac_zoho_last_sync_time');

        if (class_exists('HVAC_Logger')) {
            HVAC_Logger::info("Sync hashes reset: {$posts_cleared} post hashes, {$users_cleared} user hashes cleared", 'ZohoAdmin');
        }

        wp_send_json_success(array(
            'message' => 'Sync hashes reset successfully',
            'posts_cleared' => (int) $posts_cleared,
            'users_cleared' => (int) $users_cleared,
        ));
    }

}
?>