#![allow(
    dead_code,
    unused_imports,
    unused_variables,
    unused_assignments,
    unused
)]

//! Control Center Library
//!
//! Provides JWT authentication, user management, role-based access control,
//! and real-time WebSocket events with SurrealDB integration.

// ============================================================================
// Core Modules (Always Available with 'core' feature)
// ============================================================================

pub mod app_state;
pub mod auth;
pub mod clients;
pub mod config;
pub mod error;
pub mod handlers;
pub mod middleware;
pub mod models;
pub mod ncl_config;
pub mod services;
pub mod simple_config;
pub mod storage;

// ============================================================================
// Optional Modules (Feature-Gated)
// ============================================================================

// KMS: Key Management System
#[cfg(feature = "kms")]
pub mod kms;

// Audit: Security event logging
#[cfg(feature = "audit")]
pub mod audit;

// MFA: Multi-factor authentication
#[cfg(feature = "mfa")]
pub mod mfa;

// Compliance: Policy evaluation and compliance checking
#[cfg(feature = "compliance")]
pub mod compliance;
#[cfg(feature = "compliance")]
pub mod policies;

// Experimental: Advanced features in development
#[cfg(feature = "experimental")]
pub mod anomaly;
use std::sync::Arc;

// ============================================================================
// Re-exports - Stable API
// ============================================================================

// Core types (always available)
pub use app_state::{
    create_app_state, create_app_state_with_builder, AppStateBuilder, DefaultAppStateBuilder,
};
// Re-export auth module types
pub use auth::{
    jwt::{BlacklistStats, JwtService as NewJwtService, TokenClaims, TokenPair, TokenType},
    password::{PasswordService, PasswordStrength},
    user::{User as NewUser, UserRole, UserService as NewUserService, UserStatus},
    AuthService as NewAuthService,
};
pub use error::{ApiErrorResponse, ControlCenterError, ErrorContext, Result};
// Feature-gated type re-exports
#[cfg(feature = "mfa")]
pub use mfa::{
    MfaDeviceType, MfaService, MfaStatus, MfaVerification, TotpDevice, TotpService, WebAuthnDevice,
    WebAuthnService,
};
// Re-export simple config as the public Config type
pub use simple_config::Config;

// ============================================================================
// Internal Imports
// ============================================================================
use crate::clients::OrchestratorClient;
use crate::error::infrastructure;
use crate::handlers::websocket::WebSocketManager;
#[cfg(feature = "kms")]
use crate::kms::advanced::{AuditBackend, AuditConfig, AuditLogFormat, AuditLogLevel, AuditLogger};
#[cfg(feature = "kms")]
use crate::kms::create_http_kms_client;
use crate::services::{
    AuthService, DatabaseService, DynamicSecretsService, IacDeploymentService, IacDetectionService,
    IacRulesService, JwtService, MonitoringService, PermissionService, RoleService,
    RotationJobConfig, RotationJobScheduler, RotationScheduler, SecretSharing, SecretsService,
    UserService,
};

/// Application state shared across all handlers
#[derive(Clone)]
pub struct AppState {
    pub database_service: Arc<DatabaseService>,
    pub jwt_service: Arc<JwtService>,
    pub auth_service: Arc<AuthService>,
    pub user_service: Arc<UserService>,
    pub role_service: Arc<RoleService>,
    pub permission_service: Arc<PermissionService>,
    pub websocket_manager: Arc<WebSocketManager>,
    pub iac_detection_service: Arc<IacDetectionService>,
    pub iac_rules_service: Arc<IacRulesService>,
    pub iac_deployment_service: Arc<IacDeploymentService>,
    pub secrets_service: Arc<SecretsService>,
    pub dynamic_secrets_service: Arc<DynamicSecretsService>,
    pub rotation_scheduler: Arc<RotationScheduler>,
    pub rotation_job_scheduler: Arc<RotationJobScheduler>,
    pub secret_sharing: Arc<SecretSharing>,
    pub monitoring_service: Arc<MonitoringService>,
    pub orchestrator_client: Arc<OrchestratorClient>,
    pub config: Config,
    /// When true, auth middleware is replaced by a no-op that injects LocalUser
    /// context.
    pub solo_mode: bool,
    /// NATS bridge for task status subscription (optional feature)
    #[cfg(feature = "nats")]
    pub nats: Option<Arc<platform_nats::NatsBridge>>,
}

impl AppState {
    /// Create a new application state instance
    pub async fn new(config: Config, solo_mode: bool) -> Result<Self> {
        // Initialize database service
        let database_service = Arc::new(DatabaseService::new(config.database.clone()).await?);

        // Initialize JWT service
        let jwt_service = Arc::new(JwtService::new(config.jwt.clone())?);

        // Initialize user service
        let user_service = Arc::new(UserService::new(database_service.clone()));

        // Initialize role service
        let role_service = Arc::new(RoleService::new(database_service.clone()));

        // Initialize permission service
        let permission_service = Arc::new(PermissionService::new(database_service.clone()));

        // Initialize authentication service
        let auth_service = Arc::new(AuthService::new(
            database_service.clone(),
            jwt_service.clone(),
            user_service.clone(),
        ));

        // Initialize WebSocket manager
        let websocket_manager = Arc::new(WebSocketManager::new());

        // Initialize IaC services
        let iac_detection_service = Arc::new(IacDetectionService::new(database_service.clone()));
        let iac_rules_service = Arc::new(IacRulesService::new(database_service.clone()));
        let iac_deployment_service = Arc::new(IacDeploymentService::new(database_service.clone()));

        // Initialize KMS HTTP Client (for external KMS communication)
        // Configuration: http://localhost:9091 (default KMS service endpoint)
        // Using factory function to reduce coupling to KmsServiceClient
        let kms_client = Arc::new(create_http_kms_client("http://localhost:9091"));

        // Initialize SurrealDB Storage for secrets using config
        let storage = Arc::new(
            crate::storage::surrealdb_storage::SurrealDbPolicyStorage::new(&config)
                .await
                .map_err(|e| {
                    ControlCenterError::Infrastructure(
                        infrastructure::InfrastructureError::Configuration(format!(
                            "Failed to initialize secrets storage: {}",
                            e
                        )),
                    )
                })?,
        );

        // Initialize Audit Logger for secrets operations
        // Create minimal audit config for secrets logging
        let audit_config = AuditConfig {
            enabled: true,
            backend: AuditBackend::Stdout,
            retention_days: 30,
            log_level: AuditLogLevel::Info,
            include_data: false,
            max_file_size_mb: 100,
            format: AuditLogFormat::Json,
            database: None,
            syslog: None,
        };

        let audit_logger = Arc::new(AuditLogger::new(audit_config).await.map_err(|e| {
            ControlCenterError::Infrastructure(infrastructure::InfrastructureError::Internal(
                format!("Failed to initialize audit logger: {}", e),
            ))
        })?);

        // Initialize Secrets Service with all dependencies
        let secrets_service = Arc::new(SecretsService::new(kms_client, storage, audit_logger));

        // Initialize Orchestrator HTTP Client (Phase 2.3)
        // Configuration: orchestrator endpoint (defaults to localhost:9090)
        // TODO: Phase 3 - Add orchestrator_url to Config struct
        let orchestrator_url = "http://localhost:9090".to_string();
        let orchestrator_client = Arc::new(OrchestratorClient::new(orchestrator_url.clone()));

        // Initialize Dynamic Secrets Service (Phase 2.2)
        let dynamic_secrets_service = Arc::new(DynamicSecretsService::new(
            secrets_service.clone(),
            orchestrator_url,
        ));

        // Initialize Rotation Scheduler (Phase 3.1)
        let rotation_scheduler = Arc::new(RotationScheduler::new());

        // Initialize Rotation Job Scheduler (Phase 5)
        let rotation_job_config = RotationJobConfig {
            check_interval_secs: 3600, // Check every hour
            max_concurrent: 5,         // Max 5 concurrent rotations
            auto_start: true,          // Start automatically
        };
        let rotation_job_scheduler = Arc::new(RotationJobScheduler::new(
            rotation_scheduler.clone(),
            rotation_job_config,
        ));

        // Start the rotation job scheduler
        rotation_job_scheduler.start().await?;

        // Initialize Secret Sharing Service (Phase 3.2)
        let secret_sharing = Arc::new(SecretSharing::new());

        // Initialize Monitoring Service (Phase 3.4)
        let monitoring_service = Arc::new(MonitoringService::new());

        Ok(Self {
            database_service,
            jwt_service,
            auth_service,
            user_service,
            role_service,
            permission_service,
            websocket_manager,
            iac_detection_service,
            iac_rules_service,
            iac_deployment_service,
            secrets_service,
            dynamic_secrets_service,
            rotation_scheduler,
            rotation_job_scheduler,
            secret_sharing,
            monitoring_service,
            orchestrator_client,
            config,
            solo_mode,
            #[cfg(feature = "nats")]
            nats: {
                use platform_nats::{NatsBridge, NatsConfig};
                match NatsBridge::connect(&NatsConfig::default()).await {
                    Ok(bridge) => {
                        let bridge = std::sync::Arc::new(bridge);
                        tracing::info!("Connected to NATS");
                        Some(bridge)
                    }
                    Err(e) => {
                        tracing::warn!("NATS connection failed (bridge disabled): {}", e);
                        None
                    }
                }
            },
        })
    }

    /// Health check for all services
    pub async fn health_check(&self) -> Result<bool> {
        // Check database connection
        self.database_service.health_check().await?;

        // TODO: Add other health checks as needed

        Ok(true)
    }
}
