import os
from pathlib import Path

def load_persistent_config():
    """Load configuration from mbetterd.conf in persistent directories"""
    config_values = {}

    # Import persistent directory utilities
    try:
        from app.utils.directories import get_config_directory, get_platform_persistent_dir
        config_dir = get_config_directory()
        config_path = os.path.join(str(config_dir), 'mbetterd.conf')

        if os.path.exists(config_path):
            print(f"Loading configuration from persistent directory: {config_path}")
            with open(config_path, 'r') as f:
                for line in f:
                    line = line.strip()
                    if line and not line.startswith('#') and '=' in line:
                        key, value = line.split('=', 1)
                        config_values[key.strip()] = value.strip()
        else:
            print(f"No persistent config found at {config_path}, checking for local .env")

            # Check if we should try to copy .env to persistent directory
            local_env_path = os.path.join(os.getcwd(), '.env')
            if os.path.exists(local_env_path):
                # Try to copy .env to persistent directory
                try:
                    import shutil
                    from pathlib import Path

                    # Ensure config directory exists
                    Path(config_dir).mkdir(parents=True, exist_ok=True)

                    # Copy .env to persistent directory as mbetterd.conf
                    print(f"Copying {local_env_path} to {config_path}")
                    shutil.copy2(local_env_path, config_path)

                    # Add header to conf file
                    with open(config_path, 'r') as f:
                        content = f.read()

                    header = """# MBetter Daemon Configuration
# This file contains configuration settings for the MBetter daemon
# Format: KEY=VALUE (one per line)
# Lines starting with # are comments

"""

                    with open(config_path, 'w') as f:
                        f.write(header + content)

                    print(f"Successfully created persistent config at {config_path}")

                    # Now load from the newly created persistent config
                    with open(config_path, 'r') as f:
                        for line in f:
                            line = line.strip()
                            if line and not line.startswith('#') and '=' in line:
                                key, value = line.split('=', 1)
                                config_values[key.strip()] = value.strip()

                except Exception as copy_error:
                    print(f"Failed to copy .env to persistent directory: {str(copy_error)}")
                    print(f"Falling back to loading from local .env file: {local_env_path}")
                    # Fall back to loading from local .env
                    with open(local_env_path, 'r') as f:
                        for line in f:
                            line = line.strip()
                            if line and not line.startswith('#') and '=' in line:
                                key, value = line.split('=', 1)
                                config_values[key.strip()] = value.strip()

    except Exception as e:
        print(f"Failed to load persistent config: {str(e)}")

    # Fallback to local .env file if no config loaded yet
    if not config_values:
        local_env_path = os.path.join(os.getcwd(), '.env')
        if os.path.exists(local_env_path):
            print(f"Loading configuration from local .env file: {local_env_path}")
            with open(local_env_path, 'r') as f:
                for line in f:
                    line = line.strip()
                    if line and not line.startswith('#') and '=' in line:
                        key, value = line.split('=', 1)
                        config_values[key.strip()] = value.strip()

    # Set environment variables from config file
    for key, value in config_values.items():
        if key not in os.environ:
            os.environ[key] = value

    return config_values

def get_config_value(key: str, default: str = '') -> str:
    """Get configuration value with priority: environment > config file > default"""
    return os.environ.get(key, default)

# Load configuration
_CONFIG_VALUES = load_persistent_config()

# Import persistent directory utilities
try:
    from app.utils.directories import (
        get_uploads_directory,
        get_logs_directory,
        get_data_directory,
        get_config_directory,
        setup_persistent_directories,
        is_pyinstaller
    )
    PERSISTENT_DIRS_AVAILABLE = True
except ImportError:
    # Fallback if utilities not available
    PERSISTENT_DIRS_AVAILABLE = False

class Config:
    """Base configuration class with cross-platform persistent directory support"""
    SECRET_KEY = get_config_value('SECRET_KEY', 'dev-secret-key-change-in-production')
    
    # Database Configuration
    MYSQL_HOST = get_config_value('MYSQL_HOST', 'localhost')
    MYSQL_PORT = int(get_config_value('MYSQL_PORT', '3306'))
    MYSQL_USER = get_config_value('MYSQL_USER', 'root')
    MYSQL_PASSWORD = get_config_value('MYSQL_PASSWORD', '')
    MYSQL_DATABASE = get_config_value('MYSQL_DATABASE', 'fixture_manager')
    
    SQLALCHEMY_DATABASE_URI = f"mysql+pymysql://{MYSQL_USER}:{MYSQL_PASSWORD}@{MYSQL_HOST}:{MYSQL_PORT}/{MYSQL_DATABASE}"
    SQLALCHEMY_TRACK_MODIFICATIONS = False
    SQLALCHEMY_ENGINE_OPTIONS = {
        'pool_pre_ping': True,
        'pool_recycle': 300,
        'pool_timeout': 20,
        'max_overflow': 0
    }
    
    # Initialize persistent directories
    @classmethod
    def _get_persistent_directories(cls):
        """Get persistent directories, with fallback to current directory"""
        if PERSISTENT_DIRS_AVAILABLE:
            try:
                uploads_dir = get_uploads_directory()
                logs_dir = get_logs_directory()
                data_dir = get_data_directory()
                return {
                    'uploads': str(uploads_dir),
                    'logs': str(logs_dir),
                    'data': str(data_dir)
                }
            except Exception as e:
                import logging
                logging.warning(f"Failed to get persistent directories: {e}")
        
        # Fallback to current directory structure
        base_dir = os.path.dirname(os.path.abspath(__file__))
        return {
            'uploads': os.path.join(base_dir, 'uploads'),
            'logs': os.path.join(base_dir, 'logs'),
            'data': os.path.join(base_dir, 'data')
        }
    
    # Initialize persistent directories using helper function
    @staticmethod
    def _init_persistent_dirs():
        """Initialize persistent directories"""
        if PERSISTENT_DIRS_AVAILABLE:
            try:
                uploads_dir = get_uploads_directory()
                logs_dir = get_logs_directory()
                data_dir = get_data_directory()
                config_dir = get_config_directory()
                return {
                    'uploads': str(uploads_dir),
                    'logs': str(logs_dir),
                    'data': str(data_dir),
                    'config': str(config_dir)
                }
            except Exception as e:
                import logging
                logging.warning(f"Failed to get persistent directories: {e}")
        
        # Fallback to current directory structure
        base_dir = os.path.dirname(os.path.abspath(__file__))
        return {
            'uploads': os.path.join(base_dir, 'uploads'),
            'logs': os.path.join(base_dir, 'logs'),
            'data': os.path.join(base_dir, 'data'),
            'config': os.path.join(base_dir, 'config')
        }
    
    # File Upload Configuration - Use persistent directories
    _persistent_dirs = _init_persistent_dirs.__func__()
    UPLOAD_FOLDER = get_config_value('UPLOAD_FOLDER', _persistent_dirs['uploads'])
    MAX_CONTENT_LENGTH = int(get_config_value('MAX_CONTENT_LENGTH', str(2 * 1024 * 1024 * 1024)))  # 2GB for large ZIP files
    ALLOWED_FIXTURE_EXTENSIONS = {'csv', 'xlsx', 'xls'}
    ALLOWED_ZIP_EXTENSIONS = {'zip', '7z', 'rar'}  # Support more archive formats
    
    # Upload subdirectories
    FIXTURES_UPLOAD_FOLDER = os.path.join(UPLOAD_FOLDER, 'fixtures')
    ZIP_UPLOAD_FOLDER = os.path.join(UPLOAD_FOLDER, 'zips')
    TEMP_UPLOAD_FOLDER = os.path.join(UPLOAD_FOLDER, 'temp')
    
    # Large File Upload Configuration
    LARGE_FILE_THRESHOLD = int(get_config_value('LARGE_FILE_THRESHOLD', str(100 * 1024 * 1024)))  # 100MB
    STREAMING_UPLOAD_ENABLED = get_config_value('STREAMING_UPLOAD_ENABLED', 'True').lower() == 'true'
    UPLOAD_TIMEOUT = int(get_config_value('UPLOAD_TIMEOUT', '3600'))  # 1 hour timeout for large files
    
    # Security Configuration
    JWT_SECRET_KEY = get_config_value('JWT_SECRET_KEY', SECRET_KEY)
    JWT_ACCESS_TOKEN_EXPIRES = int(get_config_value('JWT_ACCESS_TOKEN_EXPIRES', '3600'))  # 1 hour
    BCRYPT_LOG_ROUNDS = int(get_config_value('BCRYPT_LOG_ROUNDS', '12'))
    
    # Daemon Configuration - Use persistent directories
    DAEMON_PID_FILE = get_config_value('DAEMON_PID_FILE', os.path.join(_persistent_dirs['data'], 'fixture-daemon.pid'))
    DAEMON_LOG_FILE = get_config_value('DAEMON_LOG_FILE', os.path.join(_persistent_dirs['logs'], 'fixture-daemon.log'))
    DAEMON_WORKING_DIR = get_config_value('DAEMON_WORKING_DIR', _persistent_dirs['data'])
    
    # Web Server Configuration
    HOST = get_config_value('HOST', '0.0.0.0')
    PORT = int(get_config_value('PORT', '5000'))
    DEBUG = get_config_value('DEBUG', 'False').lower() == 'true'
    
    # Logging Configuration
    LOG_LEVEL = get_config_value('LOG_LEVEL', 'INFO')
    LOG_FORMAT = '%(asctime)s - %(name)s - %(levelname)s - %(message)s'
    
    # File Processing Configuration
    CHUNK_SIZE = int(get_config_value('CHUNK_SIZE', '8192'))  # 8KB chunks for file processing
    MAX_CONCURRENT_UPLOADS = int(get_config_value('MAX_CONCURRENT_UPLOADS', '5'))
    
    # PyInstaller Detection
    IS_PYINSTALLER = is_pyinstaller() if PERSISTENT_DIRS_AVAILABLE else False
    
    @staticmethod
    def init_app(app):
        """Initialize application with configuration and set up persistent directories"""
        import logging
        logger = logging.getLogger(__name__)
        
        try:
            if PERSISTENT_DIRS_AVAILABLE:
                # Use the persistent directory system
                directories = setup_persistent_directories()
                logger.info(f"Set up persistent directories: {directories}")
                
                # Update app config with actual directory paths
                app.config['UPLOAD_FOLDER'] = str(directories['uploads'])
                app.config['FIXTURES_UPLOAD_FOLDER'] = str(directories['fixtures'])
                app.config['ZIP_UPLOAD_FOLDER'] = str(directories['zips'])
                app.config['TEMP_UPLOAD_FOLDER'] = str(directories['temp'])
                
                # Log PyInstaller detection
                if is_pyinstaller():
                    logger.info("Running from PyInstaller executable - using persistent directories")
                else:
                    logger.info("Running from Python script - using persistent directories")
            else:
                # Fallback to creating directories manually
                os.makedirs(Config.UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(Config.FIXTURES_UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(Config.ZIP_UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(Config.TEMP_UPLOAD_FOLDER, exist_ok=True)
                logger.warning("Persistent directory utilities not available - using fallback directory creation")
            
            # Create other necessary directories
            os.makedirs(os.path.dirname(Config.DAEMON_PID_FILE), exist_ok=True)
            os.makedirs(os.path.dirname(Config.DAEMON_LOG_FILE), exist_ok=True)
            os.makedirs(Config.DAEMON_WORKING_DIR, exist_ok=True)
            
        except Exception as e:
            logger.error(f"Failed to initialize directories: {e}")
            # Fallback to basic directory creation
            try:
                os.makedirs(Config.UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(Config.FIXTURES_UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(Config.ZIP_UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(Config.TEMP_UPLOAD_FOLDER, exist_ok=True)
                os.makedirs(os.path.dirname(Config.DAEMON_PID_FILE), exist_ok=True)
                os.makedirs(os.path.dirname(Config.DAEMON_LOG_FILE), exist_ok=True)
                os.makedirs(Config.DAEMON_WORKING_DIR, exist_ok=True)
            except Exception as fallback_error:
                logger.error(f"Critical: Failed to create basic directories: {fallback_error}")
                raise

class DevelopmentConfig(Config):
    """Development configuration"""
    DEBUG = True
    SQLALCHEMY_ECHO = True

class ProductionConfig(Config):
    """Production configuration with enhanced persistent directory support"""
    DEBUG = False
    SQLALCHEMY_ECHO = False
    
    @classmethod
    def init_app(cls, app):
        Config.init_app(app)
        
        # Production-specific initialization
        import logging
        from logging.handlers import RotatingFileHandler
        
        if not app.debug:
            # Ensure log directory exists
            log_file = app.config.get('DAEMON_LOG_FILE', cls.DAEMON_LOG_FILE)
            log_dir = os.path.dirname(log_file)
            os.makedirs(log_dir, exist_ok=True)
            
            file_handler = RotatingFileHandler(
                log_file,
                maxBytes=10240000,
                backupCount=10
            )
            file_handler.setFormatter(logging.Formatter(cls.LOG_FORMAT))
            file_handler.setLevel(logging.INFO)
            app.logger.addHandler(file_handler)
            
            # Log production startup info
            logger = logging.getLogger(__name__)
            logger.info("Production configuration initialized")
            if PERSISTENT_DIRS_AVAILABLE:
                logger.info(f"Using persistent directories - PyInstaller: {is_pyinstaller()}")
                logger.info(f"Upload folder: {app.config.get('UPLOAD_FOLDER', cls.UPLOAD_FOLDER)}")
                logger.info(f"Log file: {log_file}")

class TestingConfig(Config):
    """Testing configuration"""
    TESTING = True
    SQLALCHEMY_DATABASE_URI = 'sqlite:///:memory:'
    WTF_CSRF_ENABLED = False

config = {
    'development': DevelopmentConfig,
    'production': ProductionConfig,
    'testing': TestingConfig,
    'default': DevelopmentConfig
}