# --- START OF FILE profile_handler.py --- # profile_handler.py # Rimosso import logging # Importa il nuovo gestore della coda log import log_handler # Importa ConfigManager e costanti associate from config_manager import ConfigManager, DEFAULT_PROFILE, DEFAULT_BACKUP_DIR class ProfileHandler: """ Handles loading, saving, adding, removing profiles via ConfigManager. Uses log_handler for logging. (Nota: Alcune logiche qui potrebbero essere duplicate o gestite direttamente in GitUtility.py. Questo modulo potrebbe necessitare di revisione o rimozione se non più centrale.) """ # Rimosso logger da __init__ def __init__(self, config_manager: ConfigManager): """ Initializes the ProfileHandler. Args: config_manager (ConfigManager): Instance to interact with config file. """ # Validazione tipo input if not isinstance(config_manager, ConfigManager): # Log critico e solleva errore se config_manager non è valido msg = "ProfileHandler requires a valid ConfigManager instance." # Usa log_handler per errore critico (se già configurato altrove) # o print/raise direttamente print(f"CRITICAL ERROR: {msg}") # log_handler.log_critical(msg, func_name="__init__") # Potrebbe non funzionare qui raise TypeError(msg) self.config_manager = config_manager log_handler.log_debug("ProfileHandler initialized.", func_name="__init__") def get_profile_list(self): """Returns the list of available profile names.""" # Delega direttamente a config_manager return self.config_manager.get_profile_sections() def load_profile_data(self, profile_name): """ Loads all relevant data for a given profile name. Args: profile_name (str): The name of the profile to load. Returns: dict or None: A dictionary containing all profile settings, or None if the profile doesn't exist. """ func_name = "load_profile_data" log_handler.log_info( f"Loading data for profile: '{profile_name}'", func_name=func_name ) # Verifica esistenza profilo tramite config_manager if profile_name not in self.config_manager.get_profile_sections(): log_handler.log_error( f"Cannot load: Profile '{profile_name}' not found.", func_name=func_name ) return None # Ottieni chiavi e default da config_manager (fonte unica di verità) keys_with_defaults = self.config_manager._get_expected_keys_with_defaults() profile_data = {} # Carica ogni opzione usando ConfigManager log_handler.log_debug( f"Loading options for profile '{profile_name}'...", func_name=func_name ) for key, default_value in keys_with_defaults.items(): # Passa il default corretto profile_data[key] = self.config_manager.get_profile_option( profile_name, key, fallback=default_value ) # --- Conversione Tipi (Opzionale qui, forse meglio nel chiamante) --- # Se si decide di fare conversioni qui, assicurarsi che i valori di default # in _get_expected_keys_with_defaults siano stringhe come in .ini try: profile_data["autocommit"] = ( str(profile_data.get("autocommit", "False")).lower() == "true" ) profile_data["autobackup"] = ( str(profile_data.get("autobackup", "False")).lower() == "true" ) # Aggiungere altre conversioni se necessario (es. per interi o float) except Exception as e_conv: log_handler.log_warning( f"Error converting loaded profile data types for '{profile_name}': {e_conv}", func_name=func_name, ) # Procedi con i dati stringa originali in caso di errore di conversione log_handler.log_debug( f"Loaded data for '{profile_name}': {profile_data}", func_name=func_name ) return profile_data def save_profile_data(self, profile_name, profile_data): """ Saves the provided data dictionary to the specified profile name. Args: profile_name (str): The name of the profile to save. profile_data (dict): Dictionary containing the settings to save. Returns: bool: True on success, False on failure. """ func_name = "save_profile_data" # Validazione input if not profile_name: log_handler.log_warning( "Cannot save: No profile name provided.", func_name=func_name ) return False if not isinstance(profile_data, dict): log_handler.log_error( "Cannot save: Invalid profile data (not a dict).", func_name=func_name ) return False log_handler.log_info( f"Saving data for profile: '{profile_name}'", func_name=func_name ) try: # Itera sui dati da salvare for key, value in profile_data.items(): # Converte tipi Python in stringhe per configparser if isinstance(value, bool): value_to_save = str(value) # "True" o "False" # Aggiungere altre conversioni se necessario (es. lista in stringa separata da virgola) # elif isinstance(value, list): # value_to_save = ",".join(map(str, value)) else: # Converte in stringa, gestendo None value_to_save = str(value) if value is not None else "" # Imposta l'opzione tramite ConfigManager self.config_manager.set_profile_option(profile_name, key, value_to_save) # Salva le modifiche sul file .ini self.config_manager.save_config() log_handler.log_info( f"Profile '{profile_name}' saved successfully.", func_name=func_name ) return True except Exception as e: # Logga errore durante il salvataggio log_handler.log_exception( f"Error saving profile '{profile_name}': {e}", func_name=func_name ) # L'errore verrà probabilmente mostrato dal chiamante (GitUtility) return False def add_new_profile(self, profile_name): """ Adds a new profile with default settings. Args: profile_name (str): The name for the new profile. Returns: bool: True if added successfully, False otherwise. """ func_name = "add_new_profile" log_handler.log_info( f"Attempting to add new profile: '{profile_name}'", func_name=func_name ) # Validazione nome if not profile_name or profile_name.isspace(): log_handler.log_warning( "Add profile failed: Name cannot be empty.", func_name=func_name ) return False if profile_name in self.config_manager.get_profile_sections(): log_handler.log_warning( f"Add profile failed: '{profile_name}' already exists.", func_name=func_name, ) return False try: # Ottieni i default da ConfigManager defaults = self.config_manager._get_expected_keys_with_defaults() # Personalizza alcuni default per il nuovo profilo defaults["bundle_name"] = f"{profile_name}_repo.bundle" defaults["bundle_name_updated"] = f"{profile_name}_update.bundle" defaults["svn_working_copy_path"] = "" # Inizia vuoto defaults["usb_drive_path"] = "" # Inizia vuoto defaults["commit_message"] = ( f"Initial commit for profile {profile_name}" # Esempio messaggio ) # Aggiungi la sezione (se non esiste già - per sicurezza) self.config_manager.add_section(profile_name) # Imposta tutte le opzioni per la nuova sezione for key, value in defaults.items(): self.config_manager.set_profile_option( profile_name, key, value ) # set_profile_option gestisce la conversione a stringa # Salva il file di configurazione self.config_manager.save_config() log_handler.log_info( f"Profile '{profile_name}' added successfully with defaults.", func_name=func_name, ) return True except Exception as e: # Logga errori imprevisti durante l'aggiunta log_handler.log_exception( f"Error adding profile '{profile_name}': {e}", func_name=func_name ) return False def remove_existing_profile(self, profile_name): """ Removes an existing profile (cannot remove the default profile). Args: profile_name (str): The name of the profile to remove. Returns: bool: True if removed successfully, False otherwise. """ func_name = "remove_existing_profile" log_handler.log_info( f"Attempting to remove profile: '{profile_name}'", func_name=func_name ) # Validazioni if not profile_name: log_handler.log_warning( "Remove profile failed: No name provided.", func_name=func_name ) return False if profile_name == DEFAULT_PROFILE: log_handler.log_warning( "Remove profile failed: Cannot remove default profile.", func_name=func_name, ) return False if profile_name not in self.config_manager.get_profile_sections(): log_handler.log_warning( f"Remove profile failed: '{profile_name}' not found.", func_name=func_name, ) return False try: # Delega la rimozione a ConfigManager success = self.config_manager.remove_profile_section(profile_name) if success: # Salva la configurazione solo se la rimozione è andata a buon fine self.config_manager.save_config() log_handler.log_info( f"Profile '{profile_name}' removed successfully.", func_name=func_name, ) return True else: # ConfigManager dovrebbe aver loggato il motivo del fallimento log_handler.log_error( f"ConfigManager reported failure removing '{profile_name}'.", func_name=func_name, ) return False except Exception as e: # Logga errori imprevisti durante la rimozione log_handler.log_exception( f"Error removing profile '{profile_name}': {e}", func_name=func_name ) return False # --- END OF FILE profile_handler.py ---