from typing import Dict, Optional
from analogai.foundation.core.value_objects.time import Time


def _flatten_absolute_time_to_dict(time: Optional[Time], prefix: str) -> Dict:
    if time is None:
        return {}
    result: Dict = {}
    if time.year is not None:
        result[f"{prefix}_year"] = time.year
    if time.month is not None:
        result[f"{prefix}_month"] = time.month
    if time.day is not None:
        result[f"{prefix}_day"] = time.day
    if time.hour is not None:
        result[f"{prefix}_hour"] = time.hour
    if time.minute is not None:
        result[f"{prefix}_minute"] = time.minute
    return result

class TimeStorageMapper:
    @staticmethod
    def to_dict(time: Optional[Time]) -> Optional[Dict]:
        if time is None:
            return None
        
        result = {}
        if time.year is not None:
            result["year"] = time.year
        if time.month is not None:
            result["month"] = time.month
        if time.day is not None:
            result["day"] = time.day
        if time.hour is not None:
            result["hour"] = time.hour
        if time.minute is not None:
            result["minute"] = time.minute
        return result

    @staticmethod
    def from_dict(data: Optional[Dict]) -> Optional[Time]:
        if not data:
            return None
        return Time(
            year=data.get("year"),
            month=data.get("month"),
            day=data.get("day"),
            hour=data.get("hour"),
            minute=data.get("minute"),
        )

    @staticmethod
    def flatten_to_dict(time: Optional[Time], prefix: str) -> Dict:
        if time is None:
            return {}
        
        result = {}
        if time.year is not None:
            result[f"{prefix}_year"] = time.year
        if time.month is not None:
            result[f"{prefix}_month"] = time.month
        if time.day is not None:
            result[f"{prefix}_day"] = time.day
        if time.hour is not None:
            result[f"{prefix}_hour"] = time.hour
        if time.minute is not None:
            result[f"{prefix}_minute"] = time.minute
        return result

    @staticmethod
    def flatten_to_dict_absolute_only(time: Optional[Time], prefix: str) -> Dict:
        return _flatten_absolute_time_to_dict(time, prefix)

    @staticmethod
    def unflatten_from_dict(data: Dict, prefix: str) -> Optional[Time]:
        year = data.get(f"{prefix}_year")
        month = data.get(f"{prefix}_month")
        day = data.get(f"{prefix}_day")
        hour = data.get(f"{prefix}_hour")
        minute = data.get(f"{prefix}_minute")
        if any([year is not None, month is not None, day is not None, hour is not None, minute is not None]):
            return Time(year=year, month=month, day=day, hour=hour, minute=minute)
        return None

