"""
System Version Information Retrieval Implementation
"""

from typing import List
from diona.system.sensitive.info.SystemVersionInfo import SystemVersionInfoInterface
from diona.system.sensitive.info.models.SystemVersionInfo import SystemVersionInfo
from diona.system.sensitive.info.constants.SystemVersionInfoConstants import SystemVersionInfoConstants
from diona.system.sensitive.core import get_info_store_instance
from diona.system.sensitive.runcontext.utils import execute_command


class SystemVersionInfoImpl(SystemVersionInfoInterface):
    """System Version Information Retrieval Implementation"""
    
    def __init__(self):
        """
        Initialize system version information retriever
        """
        self.info_store = get_info_store_instance()
    
    def get_system_version_info(self) -> SystemVersionInfo:
        """
        Get system version information
        
        Returns:
            SystemVersionInfo: System version information object
        """
        if not self.can_execute():
            return SystemVersionInfo(
                error_message="Insufficient permissions to get system version info"
            )
        
        try:
            # Execute systeminfo command
            result = execute_command(
                SystemVersionInfoConstants.SYSTEMINFO_COMMAND,
                encoding=SystemVersionInfoConstants.DEFAULT_ENCODING
            )
            
            if not result.success:
                return SystemVersionInfo(
                    error_message=f"{SystemVersionInfoConstants.ERROR_EXECUTING_COMMAND}: {result.error}"
                )
            
            # Parse output
            return self._parse_systeminfo_output(result.output)
            
        except Exception as e:
            return SystemVersionInfo(
                error_message=f"{SystemVersionInfoConstants.ERROR_PARSING_OUTPUT}: {str(e)}"
            )
    
    def can_execute(self) -> bool:
        """
        Check if system version information retrieval can be executed
        
        Returns:
            bool: Whether execution is possible
        """
        context_info = self.info_store.get_context_info()
        if context_info:
            # System version information retrieval is available to all users
            return True
        return False
    
    def _parse_systeminfo_output(self, output: str) -> SystemVersionInfo:
        """
        Parse systeminfo command output
        
        Args:
            output: Command output
        
        Returns:
            SystemVersionInfo: System version information object
        """
        info = SystemVersionInfo()
        lines = output.split('\n')
        
        # Parse basic information
        for line in lines:
            line = line.strip()
            
            if SystemVersionInfoConstants.OS_NAME_PATTERN in line:
                info.os_name = self._extract_value(line, SystemVersionInfoConstants.OS_NAME_PATTERN)
            elif SystemVersionInfoConstants.OS_VERSION_PATTERN in line:
                info.os_version = self._extract_value(line, SystemVersionInfoConstants.OS_VERSION_PATTERN)
            elif SystemVersionInfoConstants.OS_MANUFACTURER_PATTERN in line:
                info.os_manufacturer = self._extract_value(line, SystemVersionInfoConstants.OS_MANUFACTURER_PATTERN)
            elif SystemVersionInfoConstants.OS_CONFIGURATION_PATTERN in line:
                info.os_configuration = self._extract_value(line, SystemVersionInfoConstants.OS_CONFIGURATION_PATTERN)
            elif SystemVersionInfoConstants.OS_BUILD_TYPE_PATTERN in line:
                info.os_build_type = self._extract_value(line, SystemVersionInfoConstants.OS_BUILD_TYPE_PATTERN)
            elif SystemVersionInfoConstants.REGISTERED_OWNER_PATTERN in line:
                info.registered_owner = self._extract_value(line, SystemVersionInfoConstants.REGISTERED_OWNER_PATTERN)
            elif SystemVersionInfoConstants.REGISTERED_ORGANIZATION_PATTERN in line:
                info.registered_organization = self._extract_value(line, SystemVersionInfoConstants.REGISTERED_ORGANIZATION_PATTERN)
            elif SystemVersionInfoConstants.PRODUCT_ID_PATTERN in line:
                info.product_id = self._extract_value(line, SystemVersionInfoConstants.PRODUCT_ID_PATTERN)
            elif SystemVersionInfoConstants.ORIGINAL_INSTALL_DATE_PATTERN in line:
                info.original_install_date = self._extract_value(line, SystemVersionInfoConstants.ORIGINAL_INSTALL_DATE_PATTERN)
            elif SystemVersionInfoConstants.SYSTEM_BOOT_TIME_PATTERN in line:
                info.system_boot_time = self._extract_value(line, SystemVersionInfoConstants.SYSTEM_BOOT_TIME_PATTERN)
            elif SystemVersionInfoConstants.SYSTEM_MANUFACTURER_PATTERN in line:
                info.system_manufacturer = self._extract_value(line, SystemVersionInfoConstants.SYSTEM_MANUFACTURER_PATTERN)
            elif SystemVersionInfoConstants.SYSTEM_MODEL_PATTERN in line:
                info.system_model = self._extract_value(line, SystemVersionInfoConstants.SYSTEM_MODEL_PATTERN)
            elif SystemVersionInfoConstants.SYSTEM_TYPE_PATTERN in line:
                info.system_type = self._extract_value(line, SystemVersionInfoConstants.SYSTEM_TYPE_PATTERN)
            elif SystemVersionInfoConstants.PROCESSORS_PATTERN in line:
                info.processors = self._extract_value(line, SystemVersionInfoConstants.PROCESSORS_PATTERN)
            elif SystemVersionInfoConstants.BIOS_VERSION_PATTERN in line:
                info.bios_version = self._extract_value(line, SystemVersionInfoConstants.BIOS_VERSION_PATTERN)
            elif SystemVersionInfoConstants.WINDOWS_DIRECTORY_PATTERN in line:
                info.windows_directory = self._extract_value(line, SystemVersionInfoConstants.WINDOWS_DIRECTORY_PATTERN)
            elif SystemVersionInfoConstants.SYSTEM_DIRECTORY_PATTERN in line:
                info.system_directory = self._extract_value(line, SystemVersionInfoConstants.SYSTEM_DIRECTORY_PATTERN)
            elif SystemVersionInfoConstants.BOOT_DEVICE_PATTERN in line:
                info.boot_device = self._extract_value(line, SystemVersionInfoConstants.BOOT_DEVICE_PATTERN)
            elif SystemVersionInfoConstants.SYSTEM_LOCALE_PATTERN in line:
                info.system_locale = self._extract_value(line, SystemVersionInfoConstants.SYSTEM_LOCALE_PATTERN)
            elif SystemVersionInfoConstants.INPUT_LOCALE_PATTERN in line:
                info.input_locale = self._extract_value(line, SystemVersionInfoConstants.INPUT_LOCALE_PATTERN)
            elif SystemVersionInfoConstants.TIME_ZONE_PATTERN in line:
                info.time_zone = self._extract_value(line, SystemVersionInfoConstants.TIME_ZONE_PATTERN)
            elif SystemVersionInfoConstants.TOTAL_PHYSICAL_MEMORY_PATTERN in line:
                info.total_physical_memory = self._extract_value(line, SystemVersionInfoConstants.TOTAL_PHYSICAL_MEMORY_PATTERN)
            elif SystemVersionInfoConstants.AVAILABLE_PHYSICAL_MEMORY_PATTERN in line:
                info.available_physical_memory = self._extract_value(line, SystemVersionInfoConstants.AVAILABLE_PHYSICAL_MEMORY_PATTERN)
            elif SystemVersionInfoConstants.VIRTUAL_MEMORY_MAX_SIZE_PATTERN in line:
                info.virtual_memory_max_size = self._extract_value(line, SystemVersionInfoConstants.VIRTUAL_MEMORY_MAX_SIZE_PATTERN)
            elif SystemVersionInfoConstants.VIRTUAL_MEMORY_AVAILABLE_PATTERN in line:
                info.virtual_memory_available = self._extract_value(line, SystemVersionInfoConstants.VIRTUAL_MEMORY_AVAILABLE_PATTERN)
            elif SystemVersionInfoConstants.VIRTUAL_MEMORY_IN_USE_PATTERN in line:
                info.virtual_memory_in_use = self._extract_value(line, SystemVersionInfoConstants.VIRTUAL_MEMORY_IN_USE_PATTERN)
            elif SystemVersionInfoConstants.PAGE_FILE_LOCATIONS_PATTERN in line:
                info.page_file_locations = self._extract_value(line, SystemVersionInfoConstants.PAGE_FILE_LOCATIONS_PATTERN)
            elif SystemVersionInfoConstants.DOMAIN_PATTERN in line:
                info.domain = self._extract_value(line, SystemVersionInfoConstants.DOMAIN_PATTERN)
            elif SystemVersionInfoConstants.LOGON_SERVER_PATTERN in line:
                info.logon_server = self._extract_value(line, SystemVersionInfoConstants.LOGON_SERVER_PATTERN)
        
        # 解析修补程序和网络卡信息（这些可能需要特殊处理）
        info.hotfixes = self._extract_hotfixes(output)
        info.network_cards = self._extract_network_cards(output)
        
        return info
    
    def _extract_value(self, line: str, pattern: str) -> str:
        """
        从行中提取值
        
        Args:
            line: 包含值的行
            pattern: 模式字符串
        
        Returns:
            str: 提取的值
        """
        if pattern in line:
            return line.split(pattern, 1)[1].strip()
        return None
    
    def _extract_hotfixes(self, output: str) -> List[str]:
        """
        提取修补程序信息
        
        Args:
            output: 命令输出
        
        Returns:
            List[str]: 修补程序列表
        """
        hotfixes = []
        lines = output.split('\n')
        in_hotfixes = False
        
        for line in lines:
            line = line.strip()
            if SystemVersionInfoConstants.HOTFIXES_PATTERN in line:
                in_hotfixes = True
                continue
            elif in_hotfixes:
                if not line or SystemVersionInfoConstants.NETWORK_CARD_PATTERN in line:
                    break
                hotfixes.append(line)
        
        return hotfixes
    
    def _extract_network_cards(self, output: str) -> List[str]:
        """
        提取网络卡信息
        
        Args:
            output: 命令输出
        
        Returns:
            List[str]: 网络卡列表
        """
        network_cards = []
        lines = output.split('\n')
        in_network_cards = False
        
        for line in lines:
            line = line.strip()
            if SystemVersionInfoConstants.NETWORK_CARD_PATTERN in line:
                in_network_cards = True
                continue
            elif in_network_cards:
                if not line:
                    break
                network_cards.append(line)
        
        return network_cards