import unittest
from analogai.foundation.modules.direct_statement.direct_statement import DirectStatement as Statement
from analogai.foundation.modules.notion.notion import Notion
from analogai.foundation.modules.belief.belief import Belief
from analogai.foundation.core.value_objects.time import Time
from analogai.foundation.core.value_objects.modifier import Modifier
from analogai.foundation.core.value_objects.relation import Relation
from analogai.foundation.common.enums.deontic_modality import DeonticModality
from analogai.foundation.infrastructure.mappers.statement_storage_mapper import StatementStorageMapper
from analogai.foundation.infrastructure.mappers.time_storage_mapper import TimeStorageMapper

class TestStorageMappersWithModifier(unittest.TestCase):
    
    def setUp(self):
        self.user_id = "user1"
        self.agent_id = "agent1"
        self.subject_notion = Notion(user_id=self.user_id, agent_id=self.agent_id, caption="Source", id="source1")
        self.complement_notion = Notion(user_id=self.user_id, agent_id=self.agent_id, caption="Target", id="target1")
    
    def test_statement_mapper_with_location(self):
        modifier = Modifier(location="New York")
        statement = Statement(
            user_id=self.user_id,
            agent_id=self.agent_id,
            subject_notion=self.subject_notion,
            relation=Relation.from_string("is"),
            complement_notion=self.complement_notion,
            probability=0.8,
            validity=0.9,
            modifier=modifier
        )
        
        data = StatementStorageMapper.to_dict(statement)
        restored = StatementStorageMapper.from_dict(data)
        
        self.assertEqual(restored.location, "New York")
    
    def test_statement_mapper_with_time(self):
        from_time = Time(year=2024, month=1, day=1, hour=10, minute=30)
        to_time = Time(year=2024, month=12, day=31, hour=23, minute=59)
        modifier = Modifier(from_time=from_time, to_time=to_time)
        statement = Statement(
            user_id=self.user_id,
            agent_id=self.agent_id,
            subject_notion=self.subject_notion,
            relation=Relation.from_string("is"),
            complement_notion=self.complement_notion,
            probability=0.8,
            validity=0.9,
            modifier=modifier
        )
        
        data = StatementStorageMapper.to_dict(statement)
        restored = StatementStorageMapper.from_dict(data)
        
        self.assertIsNotNone(restored.from_time)
        self.assertEqual(restored.from_time.year, 2024)
        self.assertEqual(restored.from_time.month, 1)
        self.assertEqual(restored.from_time.day, 1)
        self.assertEqual(restored.from_time.hour, 10)
        self.assertEqual(restored.from_time.minute, 30)
        self.assertIsNotNone(restored.to_time)
        self.assertEqual(restored.to_time.year, 2024)
        self.assertEqual(restored.to_time.month, 12)
        self.assertEqual(restored.to_time.day, 31)
        self.assertEqual(restored.to_time.hour, 23)
        self.assertEqual(restored.to_time.minute, 59)
    
    def test_statement_mapper_with_deontic_modality(self):
        modifier = Modifier(deontic_modality=DeonticModality.OBLIGATORY)
        statement = Statement(
            user_id=self.user_id,
            agent_id=self.agent_id,
            subject_notion=self.subject_notion,
            relation=Relation.from_string("is"),
            complement_notion=self.complement_notion,
            probability=0.8,
            validity=0.9,
            modifier=modifier
        )
        
        data = StatementStorageMapper.to_dict(statement)
        restored = StatementStorageMapper.from_dict(data)
        
        self.assertEqual(restored.deontic_modality, DeonticModality.OBLIGATORY)
    
    def test_statement_mapper_with_all_fields(self):
        from_time = Time(year=2024, month=1)
        to_time = Time(year=2024, month=12)
        modifier = Modifier(
            location="Paris",
            from_time=from_time,
            to_time=to_time,
            deontic_modality=DeonticModality.PERMITTED
        )
        statement = Statement(
            user_id=self.user_id,
            agent_id=self.agent_id,
            subject_notion=self.subject_notion,
            relation=Relation.from_string("is"),
            complement_notion=self.complement_notion,
            probability=0.8,
            validity=0.9,
            modifier=modifier
        )
        
        data = StatementStorageMapper.to_dict(statement)
        restored = StatementStorageMapper.from_dict(data)
        
        self.assertEqual(restored.location, "Paris")
        self.assertIsNotNone(restored.from_time)
        self.assertEqual(restored.from_time.year, 2024)
        self.assertEqual(restored.from_time.month, 1)
        self.assertIsNotNone(restored.to_time)
        self.assertEqual(restored.to_time.year, 2024)
        self.assertEqual(restored.to_time.month, 12)
        self.assertEqual(restored.deontic_modality, DeonticModality.PERMITTED)
    
    def test_statement_mapper_without_optional_fields(self):
        statement = Statement(
            user_id=self.user_id,
            agent_id=self.agent_id,
            subject_notion=self.subject_notion,
            relation=Relation.from_string("is"),
            complement_notion=self.complement_notion,
            probability=0.8,
            validity=0.9
        )
        
        data = StatementStorageMapper.to_dict(statement)
        restored = StatementStorageMapper.from_dict(data)
        
        self.assertIsNone(restored.location)
        self.assertIsNone(restored.from_time)
        self.assertIsNone(restored.to_time)
        self.assertIsNone(restored.deontic_modality)
    
    def test_time_mapper_to_dict(self):
        time = Time(year=2024, month=1, day=1, hour=10, minute=30)
        data = TimeStorageMapper.to_dict(time)
        
        self.assertEqual(data["year"], 2024)
        self.assertEqual(data["month"], 1)
        self.assertEqual(data["day"], 1)
        self.assertEqual(data["hour"], 10)
        self.assertEqual(data["minute"], 30)
    
    def test_time_mapper_from_dict(self):
        data = {"year": 2024, "month": 1, "day": 1, "hour": 10, "minute": 30}
        time = TimeStorageMapper.from_dict(data)
        
        self.assertEqual(time.year, 2024)
        self.assertEqual(time.month, 1)
        self.assertEqual(time.day, 1)
        self.assertEqual(time.hour, 10)
        self.assertEqual(time.minute, 30)
    
    def test_time_mapper_partial(self):
        time = Time(year=2024, month=1)
        data = TimeStorageMapper.to_dict(time)
        restored = TimeStorageMapper.from_dict(data)
        
        self.assertEqual(restored.year, 2024)
        self.assertEqual(restored.month, 1)
        self.assertIsNone(restored.day)
        self.assertIsNone(restored.hour)
        self.assertIsNone(restored.minute)
    
    def test_time_mapper_none(self):
        data = TimeStorageMapper.to_dict(None)
        self.assertIsNone(data)
        
        time = TimeStorageMapper.from_dict(None)
        self.assertIsNone(time)
    
if __name__ == '__main__':
    unittest.main()

