/**
 * WordPress Utilities for HVAC Testing Framework
 * 
 * Provides WordPress-specific functionality:
 * - WP-CLI integration for database management
 * - Cache clearing and rewrite rule flushing
 * - Test data seeding and cleanup
 * - User management and role assignments
 * 
 * @package HVAC_Community_Events
 * @version 2.0.0
 * @created 2025-08-27
 */

const { exec } = require('child_process');
const { promisify } = require('util');
const fs = require('fs').promises;
const path = require('path');
const ConfigManager = require('../core/ConfigManager');

const execAsync = promisify(exec);

class WordPressUtils {
    constructor() {
        this.config = ConfigManager;
        this.wpCliPath = this.config.get('wordpress.cliPath', 'wp');
        this.baseUrl = this.config.get('app.baseUrl');
        this.timeout = 30000; // 30 seconds for WP-CLI commands
    }
    
    /**
     * Execute WP-CLI command with error handling
     */
    async executeWpCli(command, options = {}) {
        const fullCommand = `${this.wpCliPath} ${command} --url="${this.baseUrl}" --allow-root`;
        
        try {
            console.log(`🔧 WP-CLI: ${command}`);
            const { stdout, stderr } = await execAsync(fullCommand, {
                timeout: options.timeout || this.timeout,
                cwd: options.cwd || process.cwd()
            });
            
            if (stderr && !options.ignoreStderr) {
                console.warn(`⚠️ WP-CLI Warning: ${stderr}`);
            }
            
            return stdout.trim();
        } catch (error) {
            console.error(`❌ WP-CLI Error (${command}):`, error.message);
            throw new Error(`WP-CLI command failed: ${command} - ${error.message}`);
        }
    }
    
    /**
     * Flush WordPress rewrite rules
     */
    async flushRewriteRules() {
        try {
            await this.executeWpCli('rewrite flush');
            console.log('✅ Rewrite rules flushed');
        } catch (error) {
            console.warn('Could not flush rewrite rules:', error.message);
        }
    }
    
    /**
     * Clear WordPress cache (if caching plugin is available)
     */
    async clearCache() {
        const cacheCommands = [
            'cache flush',                    // Object cache
            'transient delete --all',        // Transients
            'rewrite flush'                  // Rewrite rules
        ];
        
        for (const command of cacheCommands) {
            try {
                await this.executeWpCli(command, { ignoreStderr: true });
            } catch (error) {
                // Cache clearing might fail if no cache plugin is installed
                console.log(`Cache command skipped: ${command}`);
            }
        }
        
        console.log('🗑️ WordPress cache cleared');
    }
    
    /**
     * Create test user with specific role
     */
    async createTestUser(username, email, role, password = null) {
        // Generate password if not provided
        if (!password) {
            password = `Test${role}123!`;
        }
        
        try {
            // Check if user already exists
            const userExists = await this.executeWpCli(`user get ${username}`, { ignoreStderr: true })
                .then(() => true)
                .catch(() => false);
            
            if (userExists) {
                console.log(`👤 User already exists: ${username}`);
                
                // Update user role if needed
                await this.executeWpCli(`user set-role ${username} ${role}`);
                
                return { username, email, password, existed: true };
            }
            
            // Create new user
            await this.executeWpCli(`user create ${username} ${email} --role=${role} --user_pass="${password}"`);
            
            console.log(`✅ Created test user: ${username} (${role})`);
            return { username, email, password, existed: false };
            
        } catch (error) {
            throw new Error(`Failed to create test user ${username}: ${error.message}`);
        }
    }
    
    /**
     * Delete test user
     */
    async deleteTestUser(username) {
        try {
            await this.executeWpCli(`user delete ${username} --yes`);
            console.log(`🗑️ Deleted test user: ${username}`);
        } catch (error) {
            console.warn(`Could not delete user ${username}:`, error.message);
        }
    }
    
    /**
     * Set up test data for HVAC plugin
     */
    async seedTestData(testId) {
        console.log(`🌱 Seeding test data for: ${testId}`);
        
        try {
            // Create test events
            await this.createTestEvents(testId);
            
            // Create test venues
            await this.createTestVenues(testId);
            
            // Create test organizers
            await this.createTestOrganizers(testId);
            
            console.log('✅ Test data seeded successfully');
        } catch (error) {
            console.error('❌ Failed to seed test data:', error.message);
            throw error;
        }
    }
    
    /**
     * Create test events
     */
    async createTestEvents(testId) {
        const events = [
            {
                title: `Test HVAC Training Event - ${testId}`,
                content: 'Test event for automated testing',
                status: 'publish',
                meta: {
                    '_hvac_test_id': testId,
                    '_hvac_test_event': '1'
                }
            }
        ];
        
        for (const event of events) {
            try {
                // Create the event post
                const postCommand = `post create --post_type=tribe_events --post_title="${event.title}" --post_content="${event.content}" --post_status=${event.status} --porcelain`;
                const postId = await this.executeWpCli(postCommand);
                
                // Add meta fields
                for (const [key, value] of Object.entries(event.meta)) {
                    await this.executeWpCli(`post meta add ${postId} ${key} "${value}"`);
                }
                
                console.log(`📅 Created test event: ${event.title} (ID: ${postId})`);
            } catch (error) {
                console.warn(`Could not create test event: ${event.title}`, error.message);
            }
        }
    }
    
    /**
     * Create test venues
     */
    async createTestVenues(testId) {
        const venues = [
            {
                title: `Test Venue - ${testId}`,
                content: 'Test venue for automated testing',
                meta: {
                    '_hvac_test_id': testId,
                    '_VenueAddress': '123 Test Street',
                    '_VenueCity': 'Test City',
                    '_VenueState': 'Test State',
                    '_VenueZip': '12345'
                }
            }
        ];
        
        for (const venue of venues) {
            try {
                const postCommand = `post create --post_type=tribe_venue --post_title="${venue.title}" --post_content="${venue.content}" --post_status=publish --porcelain`;
                const postId = await this.executeWpCli(postCommand);
                
                // Add meta fields
                for (const [key, value] of Object.entries(venue.meta)) {
                    await this.executeWpCli(`post meta add ${postId} ${key} "${value}"`);
                }
                
                console.log(`🏢 Created test venue: ${venue.title} (ID: ${postId})`);
            } catch (error) {
                console.warn(`Could not create test venue: ${venue.title}`, error.message);
            }
        }
    }
    
    /**
     * Create test organizers
     */
    async createTestOrganizers(testId) {
        const organizers = [
            {
                title: `Test Organizer - ${testId}`,
                content: 'Test organizer for automated testing',
                meta: {
                    '_hvac_test_id': testId,
                    '_OrganizerPhone': '555-123-4567',
                    '_OrganizerEmail': `test-organizer-${testId}@example.com`
                }
            }
        ];
        
        for (const organizer of organizers) {
            try {
                const postCommand = `post create --post_type=tribe_organizer --post_title="${organizer.title}" --post_content="${organizer.content}" --post_status=publish --porcelain`;
                const postId = await this.executeWpCli(postCommand);
                
                // Add meta fields
                for (const [key, value] of Object.entries(organizer.meta)) {
                    await this.executeWpCli(`post meta add ${postId} ${key} "${value}"`);
                }
                
                console.log(`👤 Created test organizer: ${organizer.title} (ID: ${postId})`);
            } catch (error) {
                console.warn(`Could not create test organizer: ${organizer.title}`, error.message);
            }
        }
    }
    
    /**
     * Clean up test data
     */
    async cleanupTestData(testId) {
        console.log(`🧹 Cleaning up test data for: ${testId}`);
        
        try {
            // Find and delete test posts
            const testPosts = await this.executeWpCli(`post list --meta_key=_hvac_test_id --meta_value="${testId}" --field=ID`);
            
            if (testPosts.trim()) {
                const postIds = testPosts.split('\n').filter(id => id.trim());
                
                for (const postId of postIds) {
                    await this.executeWpCli(`post delete ${postId} --force`);
                }
                
                console.log(`🗑️ Deleted ${postIds.length} test posts`);
            }
            
            // Clean up orphaned meta
            await this.executeWpCli(`db query "DELETE FROM wp_postmeta WHERE meta_key = '_hvac_test_id' AND meta_value = '${testId}'"`);
            
        } catch (error) {
            console.warn('Could not fully clean up test data:', error.message);
        }
    }
    
    /**
     * Check if plugin is active
     */
    async isPluginActive(pluginName) {
        try {
            const activePlugins = await this.executeWpCli('plugin list --status=active --field=name');
            return activePlugins.includes(pluginName);
        } catch (error) {
            console.warn(`Could not check plugin status for ${pluginName}:`, error.message);
            return false;
        }
    }
    
    /**
     * Activate plugin
     */
    async activatePlugin(pluginName) {
        try {
            await this.executeWpCli(`plugin activate ${pluginName}`);
            console.log(`✅ Activated plugin: ${pluginName}`);
        } catch (error) {
            throw new Error(`Failed to activate plugin ${pluginName}: ${error.message}`);
        }
    }
    
    /**
     * Get WordPress version
     */
    async getWordPressVersion() {
        try {
            const version = await this.executeWpCli('core version');
            return version.trim();
        } catch (error) {
            console.warn('Could not get WordPress version:', error.message);
            return 'unknown';
        }
    }
    
    /**
     * Update database after schema changes
     */
    async updateDatabase() {
        try {
            await this.executeWpCli('core update-db');
            console.log('✅ Database updated');
        } catch (error) {
            console.warn('Could not update database:', error.message);
        }
    }
    
    /**
     * Import test data from SQL file
     */
    async importDatabase(sqlFilePath) {
        try {
            const absolutePath = path.resolve(sqlFilePath);
            await this.executeWpCli(`db import "${absolutePath}"`);
            console.log(`✅ Imported database from: ${sqlFilePath}`);
        } catch (error) {
            throw new Error(`Failed to import database: ${error.message}`);
        }
    }
    
    /**
     * Export database to SQL file
     */
    async exportDatabase(outputPath) {
        try {
            const absolutePath = path.resolve(outputPath);
            await this.executeWpCli(`db export "${absolutePath}"`);
            console.log(`✅ Exported database to: ${outputPath}`);
            return absolutePath;
        } catch (error) {
            throw new Error(`Failed to export database: ${error.message}`);
        }
    }
    
    /**
     * Reset database to clean state
     */
    async resetDatabase() {
        try {
            await this.executeWpCli('db reset --yes');
            console.log('✅ Database reset to clean state');
        } catch (error) {
            throw new Error(`Failed to reset database: ${error.message}`);
        }
    }
    
    /**
     * Get site URL
     */
    async getSiteUrl() {
        try {
            return await this.executeWpCli('option get siteurl');
        } catch (error) {
            console.warn('Could not get site URL:', error.message);
            return this.baseUrl;
        }
    }
    
    /**
     * Set WordPress option
     */
    async setOption(optionName, optionValue) {
        try {
            await this.executeWpCli(`option update ${optionName} "${optionValue}"`);
            console.log(`✅ Set option: ${optionName} = ${optionValue}`);
        } catch (error) {
            console.warn(`Could not set option ${optionName}:`, error.message);
        }
    }
    
    /**
     * Get WordPress option
     */
    async getOption(optionName) {
        try {
            return await this.executeWpCli(`option get ${optionName}`);
        } catch (error) {
            console.warn(`Could not get option ${optionName}:`, error.message);
            return null;
        }
    }
    
    /**
     * Run WordPress cron
     */
    async runCron() {
        try {
            await this.executeWpCli('cron event run --due-now');
            console.log('✅ WordPress cron executed');
        } catch (error) {
            console.warn('Could not run cron:', error.message);
        }
    }
    
    /**
     * Check WordPress environment health
     */
    async checkHealth() {
        const health = {
            wpVersion: 'unknown',
            pluginsActive: false,
            databaseConnected: false,
            writableUploads: false
        };
        
        try {
            // Check WordPress version
            health.wpVersion = await this.getWordPressVersion();
            
            // Check if HVAC plugin is active
            health.pluginsActive = await this.isPluginActive('hvac-community-events');
            
            // Check database connection
            try {
                await this.executeWpCli('db check');
                health.databaseConnected = true;
            } catch (error) {
                health.databaseConnected = false;
            }
            
            // Check uploads directory
            try {
                await this.executeWpCli('eval "wp_upload_dir();"');
                health.writableUploads = true;
            } catch (error) {
                health.writableUploads = false;
            }
            
        } catch (error) {
            console.warn('Health check incomplete:', error.message);
        }
        
        console.log('🏥 WordPress Health Check:', health);
        return health;
    }
}

module.exports = WordPressUtils;