//! Command Structure - Comprehensive CLI decomposition architecture
//!
//! This module provides the complete command structure decomposition to reduce
//! the main CLI module from 145 functions and 10,304 lines to a manageable size.
//!
//! Architecture:
//! - `CommandExecutor`: Main command execution orchestrator
//! - `CommandRegistry`: Registry of all available commands  
//! - `CommandGroup`: Logical grouping of related commands
//! - `ModularHandlers`: Individual command implementation modules

use crate::cli::commands::ScaffoldCommands;
use crate::cli::{AnalyzeCommands, Commands};
use crate::stateless_server::StatelessTemplateServer;
use anyhow::Result;
use std::sync::Arc;

/// Main command executor that orchestrates all CLI operations
pub struct CommandExecutor {
    server: Arc<StatelessTemplateServer>,
    registry: CommandRegistry,
}

/// Registry that manages all available commands and their handlers
#[derive(Default)]
pub struct CommandRegistry {
    generate_handlers: GenerateCommandGroup,
    analyze_handlers: AnalyzeCommandGroup,
    utility_handlers: UtilityCommandGroup,
    demo_handlers: DemoCommandGroup,
}

/// Command group for generation operations (generate, scaffold, validate)
pub struct GenerateCommandGroup;

/// Command group for analysis operations (complexity, churn, dead-code, etc.)
pub struct AnalyzeCommandGroup;

/// Command group for utility operations (list, search, context, serve)
pub struct UtilityCommandGroup;

/// Command group for demo and quality gate operations
pub struct DemoCommandGroup;

impl CommandExecutor {
    /// Create new command executor with server instance
    #[must_use]
    pub fn new(server: Arc<StatelessTemplateServer>) -> Self {
        Self {
            server,
            registry: CommandRegistry::default(),
        }
    }

    /// Execute a command using the modular dispatch architecture
    pub async fn execute(&self, command: Commands) -> Result<()> {
        match command {
            // Generation commands
            Commands::Generate {
                category,
                template,
                params,
                output,
                create_dirs,
            } => {
                self.registry
                    .generate_handlers
                    .handle_generate(
                        self.server.clone(),
                        category,
                        template,
                        params,
                        output,
                        create_dirs,
                    )
                    .await
            }
            Commands::Scaffold { command } => {
                match command {
                    ScaffoldCommands::Project {
                        toolchain,
                        templates,
                        params,
                        parallel,
                    } => {
                        self.registry
                            .generate_handlers
                            .handle_scaffold(
                                self.server.clone(),
                                toolchain,
                                templates,
                                params,
                                parallel,
                            )
                            .await
                    }
                    ScaffoldCommands::Agent {
                        name,
                        template,
                        features,
                        quality,
                        output,
                        force,
                        dry_run,
                        interactive,
                        deterministic_core,
                        probabilistic_wrapper,
                    } => {
                        // TICKET-PMAT-5030: Wire up agent scaffolding
                        let params = super::handlers::ScaffoldAgentParams {
                            name,
                            template,
                            features,
                            quality,
                            output,
                            force,
                            dry_run,
                            interactive,
                            deterministic_core,
                            probabilistic_wrapper,
                        };
                        super::handlers::handle_scaffold_agent(params).await
                    }
                    ScaffoldCommands::Wasm {
                        name,
                        framework,
                        features,
                        quality,
                        output,
                        force,
                        dry_run,
                    } => {
                        // TICKET-PMAT-5031: Wire up WASM scaffolding
                        let params = super::handlers::ScaffoldWasmParams {
                            name,
                            framework,
                            features,
                            quality,
                            output,
                            force,
                            dry_run,
                        };
                        super::handlers::handle_scaffold_wasm(params).await
                    }
                    ScaffoldCommands::ListTemplates => {
                        super::handlers::handle_list_agent_templates().await
                    }
                    ScaffoldCommands::ValidateTemplate { path } => {
                        super::handlers::handle_validate_agent_template(path).await
                    }
                    ScaffoldCommands::ListSubagents { all } => {
                        super::handlers::subagent_handlers::list_subagents(all)
                    }
                    ScaffoldCommands::CreateSubagent { agent_name, output } => {
                        super::handlers::subagent_handlers::create_subagent(&agent_name, output)
                    }
                    ScaffoldCommands::CreateAllSubagents { output } => {
                        super::handlers::subagent_handlers::create_all_mvp_subagents(output)
                    }
                    ScaffoldCommands::ValidateSubagent { file_path } => {
                        super::handlers::subagent_handlers::validate_subagent(&file_path)
                    }
                    ScaffoldCommands::ShowToolMapping { agent } => {
                        super::handlers::subagent_handlers::show_tool_mapping(agent)
                    }
                    ScaffoldCommands::ExportToolMapping { output } => {
                        super::handlers::subagent_handlers::export_tool_mapping_json(&output)
                    }
                }
            }
            Commands::Validate { uri, params } => {
                self.registry
                    .generate_handlers
                    .handle_validate(self.server.clone(), uri, params)
                    .await
            }

            // Analysis commands
            Commands::Analyze(analyze_cmd) => {
                self.registry.analyze_handlers.execute(analyze_cmd).await
            }

            Commands::Qdd(qdd_cmd) => {
                use crate::cli::handlers::qdd_handlers;
                qdd_handlers::handle_qdd_command(qdd_cmd).await
            }

            // Utility commands
            Commands::List {
                toolchain,
                category,
                format,
            } => {
                self.registry
                    .utility_handlers
                    .handle_list(self.server.clone(), toolchain, category, format)
                    .await
            }
            Commands::Search {
                query,
                toolchain,
                limit,
            } => {
                self.registry
                    .utility_handlers
                    .handle_search(self.server.clone(), query, toolchain, limit)
                    .await
            }
            Commands::Context {
                toolchain,
                project_path,
                output,
                format,
                include_large_files,
                skip_expensive_metrics,
                language,
                languages,
            } => {
                self.registry
                    .utility_handlers
                    .handle_context(
                        toolchain,
                        project_path,
                        output,
                        format,
                        include_large_files,
                        skip_expensive_metrics,
                        language,
                        languages,
                    )
                    .await
            }
            Commands::Serve {
                port,
                host,
                cors,
                transport,
            } => {
                self.registry
                    .utility_handlers
                    .handle_serve(host, port, cors, transport)
                    .await
            }

            // Demo and quality commands
            Commands::Demo {
                path,
                url,
                repo,
                format,
                protocol,
                show_api,
                no_browser,
                port,
                cli,
                target_nodes,
                centrality_threshold,
                merge_threshold,
                debug,
                debug_output,
                skip_vendor,
                no_skip_vendor,
                max_line_length,
            } => {
                self.registry
                    .demo_handlers
                    .handle_demo(
                        self.server.clone(),
                        path,
                        url,
                        repo,
                        format,
                        protocol,
                        show_api,
                        no_browser,
                        port,
                        cli,
                        target_nodes,
                        centrality_threshold,
                        merge_threshold,
                        debug,
                        debug_output,
                        skip_vendor && !no_skip_vendor,
                        max_line_length,
                    )
                    .await
            }
            Commands::QualityGate {
                project_path,
                file,
                format,
                fail_on_violation,
                checks,
                max_dead_code,
                min_entropy,
                max_complexity_p99,
                include_provability,
                output,
                perf,
            } => {
                self.registry
                    .demo_handlers
                    .handle_quality_gate(
                        project_path,
                        file,
                        format,
                        fail_on_violation,
                        checks,
                        max_dead_code,
                        min_entropy,
                        max_complexity_p99,
                        include_provability,
                        output,
                        perf,
                    )
                    .await
            }
            Commands::Report {
                project_path,
                output_format,
                text,
                markdown,
                csv,
                include_visualizations,
                include_executive_summary,
                include_recommendations,
                analyses,
                confidence_threshold,
                output,
                perf,
            } => {
                crate::cli::handlers::enhanced_reporting_handlers::handle_generate_report(
                    project_path,
                    output_format,
                    text,
                    markdown,
                    csv,
                    include_visualizations,
                    include_executive_summary,
                    include_recommendations,
                    analyses,
                    confidence_threshold,
                    output,
                    perf,
                )
                .await
            }
            Commands::RepoScore {
                path,
                format,
                verbose,
                failures_only,
                output,
                update_badge,
                deep,
            } => {
                crate::cli::handlers::repo_score_handlers::handle_repo_score(
                    &path,
                    format,
                    verbose,
                    failures_only,
                    output.as_deref(),
                    update_badge,
                    deep,
                )
                .await
            }
            Commands::RustProjectScore {
                path,
                format,
                verbose,
                failures_only,
                output,
                full,
            } => {
                crate::cli::handlers::rust_project_score_handlers::handle_rust_project_score(
                    &path,
                    &format,
                    verbose,
                    failures_only,
                    output.as_deref(),
                    full,
                )
                .await
            }
            Commands::Diagnose(args) => self.registry.utility_handlers.handle_diagnose(args).await,
            Commands::Refactor(refactor_cmd) => {
                super::handlers::route_refactor_command(refactor_cmd).await
            }
            Commands::Enforce(enforce_cmd) => {
                super::handlers::route_enforce_command(enforce_cmd).await
            }
            Commands::Roadmap(roadmap_cmd) => {
                super::command_dispatcher::CommandDispatcher::execute_roadmap_command(roadmap_cmd)
                    .await
            }
            Commands::Test {
                suite,
                iterations,
                memory,
                throughput,
                regression,
                timeout,
                output,
                perf,
            } => {
                crate::cli::handlers::test_handlers::handle_test(
                    suite, iterations, memory, throughput, regression, timeout, output, perf,
                )
                .await
            }
            Commands::Memory { command } => {
                super::command_dispatcher::CommandDispatcher::execute_memory_command(command).await
            }
            Commands::Cache { command } => {
                super::command_dispatcher::CommandDispatcher::execute_cache_command(command).await
            }
            Commands::Telemetry {
                system,
                service,
                reset,
                test_event,
            } => super::handlers::handle_telemetry(system, service, reset, test_event).await,
            Commands::Config {
                show,
                edit,
                validate,
                reset,
                section,
                set,
                config_path,
            } => {
                super::handlers::handle_configuration(
                    show,
                    edit,
                    validate,
                    reset,
                    section,
                    set,
                    config_path,
                )
                .await
            }

            Commands::Agent { command } => super::handlers::handle_agent_command(command).await,

            Commands::Tdg {
                path,
                command,
                format,
                config,
                quiet,
                include_components,
                min_grade,
                output,
                with_git_context,
                explain,
                threshold,
                baseline,
            } => {
                let tdg_config = super::handlers::tdg_handlers::TdgCommandConfig {
                    path,
                    command,
                    format,
                    config,
                    quiet,
                    include_components,
                    min_grade,
                    output,
                    with_git_context,
                    explain,
                    threshold,
                    baseline,
                };
                super::handlers::handle_tdg_command(tdg_config).await
            }
            Commands::ValidateDocs(cmd) => {
                let exit_code = cmd.execute().await?;
                if exit_code != std::process::ExitCode::SUCCESS {
                    std::process::exit(1);
                }
                Ok(())
            }
            Commands::ValidateReadme(cmd) => {
                // Sprint 38: Hallucination detection (synchronous)
                let exit_code = cmd.execute()?;
                if exit_code != std::process::ExitCode::SUCCESS {
                    std::process::exit(1);
                }
                Ok(())
            }
            Commands::RedTeam(cmd) => {
                // Red Team Mode: Commit hallucination detection
                let exit_code = cmd.execute()?;
                if exit_code != std::process::ExitCode::SUCCESS {
                    std::process::exit(1);
                }
                Ok(())
            }
            Commands::Org(_org_cmd) => {
                #[cfg(feature = "org-intelligence")]
                {
                    crate::cli::handlers::handle_org_command(_org_cmd).await
                }
                #[cfg(not(feature = "org-intelligence"))]
                {
                    anyhow::bail!("Organizational intelligence feature is not enabled. Rebuild with --features org-intelligence")
                }
            }
            Commands::Prompt(prompt_cmd) => {
                crate::cli::handlers::handle_prompt_command(prompt_cmd).await
            }
            Commands::QualityGates {
                command,
                config,
                report,
                json,
                project_dir,
            } => {
                super::handlers::handle_quality_gates_command(
                    command,
                    config,
                    report,
                    json,
                    project_dir,
                )
                .await
            }

            Commands::Maintain { command } => {
                use super::commands::MaintainCommands;
                match command {
                    MaintainCommands::Roadmap {
                        roadmap,
                        tickets_dir,
                        validate,
                        health,
                        fix,
                        generate_tickets,
                        dry_run,
                        format,
                    } => {
                        let config =
                            super::handlers::roadmap_handler::RoadmapMaintenanceConfig::new(
                                validate,
                                health,
                                fix,
                                generate_tickets,
                                dry_run,
                            );
                        super::handlers::handle_maintain_roadmap(
                            roadmap,
                            tickets_dir,
                            config,
                            format,
                        )
                        .await
                    }
                    MaintainCommands::Health {
                        project_dir,
                        format,
                        quick,
                        all,
                        check_build,
                        check_tests,
                        check_coverage,
                        check_complexity,
                        check_satd,
                    } => {
                        let config = super::handlers::health_handler::HealthCheckConfig::new(
                            quick,
                            all,
                            check_build,
                            check_tests,
                            check_coverage,
                            check_complexity,
                            check_satd,
                        );
                        super::handlers::handle_maintain_health(project_dir, format, config).await
                    }
                    MaintainCommands::BugReport {
                        title,
                        dry_run,
                        interactive,
                        clear,
                    } => {
                        super::handlers::bug_report_handler::handle_bug_report(
                            title.as_deref(),
                            dry_run,
                            interactive,
                            clear,
                        )
                        .await
                    }
                    MaintainCommands::CleanupResources {
                        project_dir,
                        targets,
                        execute,
                        exclude,
                        min_age_days,
                        format,
                    } => {
                        super::handlers::cleanup_resources_handler::handle_cleanup_resources(
                            &project_dir,
                            &targets,
                            execute,
                            &exclude,
                            min_age_days,
                            format,
                        )
                        .await
                    }
                }
            }

            Commands::Hooks(hooks_cmd) => super::handlers::handle_hooks_command(&hooks_cmd).await,

            // Semantic search commands (PMAT-SEARCH-011)
            Commands::Embed(embed_cmd) => {
                super::command_dispatcher::CommandDispatcher::execute_embed_command(embed_cmd).await
            }
            Commands::Semantic(semantic_cmd) => {
                super::command_dispatcher::CommandDispatcher::execute_semantic_command(semantic_cmd)
                    .await
            }

            // Mutation testing command (Sprint 61)
            #[cfg(feature = "mutation-testing")]
            Commands::Mutate(args) => {
                super::handlers::mutate::handle(args, self.server.clone()).await
            }

            // Time-travel debugging commands (Sprint 74)
            Commands::Debug { command } => {
                use crate::cli::commands::DebugCommands;
                match command {
                    DebugCommands::Serve {
                        port,
                        host,
                        record_dir,
                    } => {
                        // DEBUG-002: DAP Server CLI Handler (implemented)
                        // Sprint 76 CAPTURE-003: Added record_dir support
                        super::handlers::debug_handlers::handle_debug_serve(port, host, record_dir)
                            .await
                    }
                    DebugCommands::Replay {
                        recording,
                        position,
                        interactive,
                    } => {
                        // DEBUG-003: Replay CLI Handler (implemented)
                        super::handlers::debug_handlers::handle_debug_replay(
                            recording,
                            position,
                            interactive,
                        )
                        .await
                    }
                }
            }
            // Phase 3.1: O(1) Quality Gates - CLI Integration
            Commands::ShowMetrics { .. } => {
                anyhow::bail!("ShowMetrics command should be handled by command_dispatcher.rs")
            }
            // Phase 4.1: O(1) Quality Gates - Predictive CLI
            Commands::PredictQuality { .. } => {
                anyhow::bail!("PredictQuality command should be handled by command_dispatcher.rs")
            }
            // Phase 3.4: O(1) Quality Gates - CI/CD Integration
            Commands::RecordMetric { .. } => {
                anyhow::bail!("RecordMetric command should be handled by command_dispatcher.rs")
            }
            // Issue #75: Unified GitHub/YAML workflow
            Commands::Work { command } => {
                anyhow::bail!(
                    "Work command not yet implemented in command structure: {:?}",
                    command
                )
            }
            // GH-102: QA Work - Toyota Way quality validation
            Commands::QaWork { .. } => {
                anyhow::bail!("QaWork command should be handled by command_dispatcher.rs")
            }
            // GH-96: PMAT compliance and migration system - handled by command_dispatcher.rs
            Commands::Comply { .. } => {
                anyhow::bail!("Comply command should be handled by command_dispatcher.rs")
            }

            // GH-98: Systematic test discovery and fixing - handled by command_dispatcher.rs
            Commands::TestDiscovery { .. } => {
                anyhow::bail!("TestDiscovery command should be handled by command_dispatcher.rs")
            }

            // Five Whys root cause analysis - handled by command_dispatcher.rs
            Commands::DebugFiveWhys { .. } => {
                anyhow::bail!("DebugFiveWhys command should be handled by command_dispatcher.rs")
            }

            // Fault localization - handled by command_dispatcher.rs (GH-103)
            Commands::Localize { .. } => {
                anyhow::bail!("Localize command should be handled by command_dispatcher.rs")
            }
        }
    }
}

impl Default for GenerateCommandGroup {
    fn default() -> Self {
        Self
    }
}

impl GenerateCommandGroup {
    /// Handle generate command with modular implementation
    pub async fn handle_generate(
        &self,
        server: Arc<StatelessTemplateServer>,
        category: String,
        template: String,
        params: Vec<(String, serde_json::Value)>,
        output: Option<std::path::PathBuf>,
        create_dirs: bool,
    ) -> Result<()> {
        // Delegate to generation handlers module
        crate::cli::handlers::generation_handlers::handle_generate(
            server,
            category,
            template,
            params,
            output,
            create_dirs,
        )
        .await
    }

    /// Handle scaffold command
    pub async fn handle_scaffold(
        &self,
        server: Arc<StatelessTemplateServer>,
        toolchain: String,
        templates: Vec<String>,
        params: Vec<(String, serde_json::Value)>,
        parallel: usize,
    ) -> Result<()> {
        crate::cli::handlers::generation_handlers::handle_scaffold(
            server, toolchain, templates, params, parallel,
        )
        .await
    }

    /// Handle validate command
    pub async fn handle_validate(
        &self,
        server: Arc<StatelessTemplateServer>,
        uri: String,
        params: Vec<(String, serde_json::Value)>,
    ) -> Result<()> {
        crate::cli::handlers::generation_handlers::handle_validate(server, uri, params).await
    }
}

impl Default for AnalyzeCommandGroup {
    fn default() -> Self {
        Self
    }
}

impl AnalyzeCommandGroup {
    /// Execute analysis command using modular handlers
    pub async fn execute(&self, cmd: AnalyzeCommands) -> Result<()> {
        // Delegate to analysis handlers which further delegate to specific modules
        crate::cli::handlers::analysis_handlers::route_analyze_command(cmd).await
    }
}

impl Default for UtilityCommandGroup {
    fn default() -> Self {
        Self
    }
}

impl UtilityCommandGroup {
    /// Handle list command
    pub async fn handle_list(
        &self,
        server: Arc<StatelessTemplateServer>,
        toolchain: Option<String>,
        category: Option<String>,
        format: crate::cli::OutputFormat,
    ) -> Result<()> {
        crate::cli::handlers::utility_handlers::handle_list(server, toolchain, category, format)
            .await
    }

    /// Handle search command
    pub async fn handle_search(
        &self,
        server: Arc<StatelessTemplateServer>,
        query: String,
        toolchain: Option<String>,
        limit: usize,
    ) -> Result<()> {
        crate::cli::handlers::utility_handlers::handle_search(server, query, toolchain, limit).await
    }

    /// Handle context command
    #[allow(clippy::too_many_arguments)]
    pub async fn handle_context(
        &self,
        toolchain: Option<String>,
        project_path: std::path::PathBuf,
        output: Option<std::path::PathBuf>,
        format: crate::cli::ContextFormat,
        include_large_files: bool,
        skip_expensive_metrics: bool,
        language: Option<String>,
        languages: Option<Vec<String>>,
    ) -> Result<()> {
        crate::cli::handlers::utility_handlers::handle_context(
            toolchain,
            project_path,
            output,
            format,
            include_large_files,
            skip_expensive_metrics,
            language,
            languages,
        )
        .await
    }

    /// Handle serve command
    pub async fn handle_serve(
        &self,
        host: String,
        port: u16,
        cors: bool,
        transport: crate::cli::commands::ServeTransport,
    ) -> Result<()> {
        crate::cli::handlers::utility_handlers::handle_serve(host, port, cors, transport).await
    }

    /// Handle diagnose command
    pub async fn handle_diagnose(&self, args: crate::cli::diagnose::DiagnoseArgs) -> Result<()> {
        crate::cli::handlers::utility_handlers::handle_diagnose(args).await
    }
}

impl Default for DemoCommandGroup {
    fn default() -> Self {
        Self
    }
}

impl DemoCommandGroup {
    /// Handle demo command with comprehensive parameter support
    #[allow(clippy::too_many_arguments)]
    pub async fn handle_demo(
        &self,
        server: Arc<StatelessTemplateServer>,
        path: Option<std::path::PathBuf>,
        url: Option<String>,
        repo: Option<String>,
        format: crate::cli::OutputFormat,
        protocol: crate::cli::DemoProtocol,
        show_api: bool,
        no_browser: bool,
        port: Option<u16>,
        cli: bool,
        target_nodes: usize,
        centrality_threshold: f64,
        merge_threshold: usize,
        debug: bool,
        debug_output: Option<std::path::PathBuf>,
        skip_vendor: bool,
        max_line_length: Option<usize>,
    ) -> Result<()> {
        // Use dedicated demo handlers module
        crate::cli::handlers::demo_handlers::handle_demo(
            server,
            path,
            url,
            repo,
            format,
            protocol,
            show_api,
            no_browser,
            port,
            cli,
            target_nodes,
            centrality_threshold,
            merge_threshold,
            debug,
            debug_output,
            skip_vendor,
            max_line_length,
        )
        .await
    }

    /// Handle quality gate command
    #[allow(clippy::too_many_arguments)]
    pub async fn handle_quality_gate(
        &self,
        project_path: std::path::PathBuf,
        file: Option<std::path::PathBuf>,
        format: crate::cli::QualityGateOutputFormat,
        fail_on_violation: bool,
        checks: Vec<crate::cli::QualityCheckType>,
        max_dead_code: f64,
        min_entropy: f64,
        max_complexity_p99: u32,
        include_provability: bool,
        output: Option<std::path::PathBuf>,
        perf: bool,
    ) -> Result<()> {
        // Use dedicated demo handlers module
        crate::cli::handlers::demo_handlers::handle_quality_gate(
            project_path,
            file,
            format,
            fail_on_violation,
            checks,
            max_dead_code,
            min_entropy,
            max_complexity_p99,
            include_provability,
            output,
            perf,
        )
        .await
    }
}

/// Factory for creating command executors
pub struct CommandExecutorFactory;

impl CommandExecutorFactory {
    /// Create a new command executor instance
    #[must_use]
    pub fn create(server: Arc<StatelessTemplateServer>) -> CommandExecutor {
        CommandExecutor::new(server)
    }
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_command_registry_creation() {
        let _registry = CommandRegistry::default();

        // Verify all command groups are initialized - no assertion needed
    }

    #[test]
    fn test_command_group_defaults() {
        let _generate = GenerateCommandGroup;
        let _analyze = AnalyzeCommandGroup;
        let _utility = UtilityCommandGroup;
        let _demo = DemoCommandGroup;

        // All groups should be creatable - no assertion needed
    }
}

#[cfg(test)]
mod property_tests {
    use proptest::prelude::*;

    proptest! {
        #[test]
        fn basic_property_stability(_input in ".*") {
            // Basic property test for coverage
            prop_assert!(true);
        }

        #[test]
        fn module_consistency_check(_x in 0u32..1000) {
            // Module consistency verification
            prop_assert!(_x < 1001);
        }
    }
}
