"""
Unit tests for Match Pydantic schemas.
"""

import pytest
from datetime import datetime, timezone
from pydantic import ValidationError

from app.schemas.match import (
    MatchBase,
    MatchCreate,
    MatchUpdate,
    MatchResponse,
    MatchListResponse,
    MatchStatsResponse
)


class TestMatchBase:
    """Test MatchBase schema."""
    
    def test_match_base_valid(self):
        """Test creating a valid MatchBase."""
        match_data = {
            "home_team": "PSG",
            "away_team": "Olympique de Marseille",
            "date": datetime.now(timezone.utc),
            "league": "Ligue 1",
            "status": "scheduled"
        }
        
        match = MatchBase(**match_data)
        
        assert match.home_team == "PSG"
        assert match.away_team == "Olympique de Marseille"
        assert match.league == "Ligue 1"
        assert match.status == "scheduled"
    
    def test_match_base_home_team_too_long(self):
        """Test that home_team exceeds max length."""
        with pytest.raises(ValidationError) as exc_info:
            MatchBase(
                home_team="A" * 256,  # Too long
                away_team="Olympique de Marseille",
                date=datetime.now(timezone.utc),
                league="Ligue 1",
                status="scheduled"
            )
        
        assert "at most 255 characters" in str(exc_info.value).lower()
    
    def test_match_base_away_team_empty(self):
        """Test that away_team cannot be empty."""
        with pytest.raises(ValidationError) as exc_info:
            MatchBase(
                home_team="PSG",
                away_team="",  # Empty
                date=datetime.now(timezone.utc),
                league="Ligue 1",
                status="scheduled"
            )
        
        assert "at least 1 character" in str(exc_info.value).lower()
    
    def test_match_base_status_too_long(self):
        """Test that status exceeds max length."""
        with pytest.raises(ValidationError) as exc_info:
            MatchBase(
                home_team="PSG",
                away_team="Olympique de Marseille",
                date=datetime.now(timezone.utc),
                league="Ligue 1",
                status="A" * 51  # Too long
            )
        
        assert "at most 50 characters" in str(exc_info.value).lower()


class TestMatchCreate:
    """Test MatchCreate schema."""
    
    def test_match_create_valid(self):
        """Test creating a valid MatchCreate."""
        match_data = {
            "home_team": "Barcelona",
            "away_team": "Real Madrid",
            "date": datetime.now(timezone.utc),
            "league": "La Liga",
            "status": "in_progress"
        }
        
        match = MatchCreate(**match_data)
        
        assert match.home_team == "Barcelona"
        assert match.away_team == "Real Madrid"
        assert match.status == "in_progress"


class TestMatchUpdate:
    """Test MatchUpdate schema."""
    
    def test_match_update_partial(self):
        """Test updating only some fields."""
        update_data = {
            "status": "completed"
        }
        
        match_update = MatchUpdate(**update_data)
        
        assert match_update.status == "completed"
        assert match_update.home_team is None
        assert match_update.away_team is None
    
    def test_match_update_all_fields(self):
        """Test updating all fields."""
        update_data = {
            "home_team": "Manchester City",
            "away_team": "Liverpool",
            "date": datetime.now(timezone.utc),
            "league": "Premier League",
            "status": "in_progress"
        }
        
        match_update = MatchUpdate(**update_data)
        
        assert match_update.home_team == "Manchester City"
        assert match_update.away_team == "Liverpool"
        assert match_update.league == "Premier League"
        assert match_update.status == "in_progress"
    
    def test_match_update_empty(self):
        """Test that MatchUpdate can be empty."""
        match_update = MatchUpdate()
        
        assert match_update.home_team is None
        assert match_update.away_team is None
        assert match_update.date is None
        assert match_update.league is None
        assert match_update.status is None


class TestMatchResponse:
    """Test MatchResponse schema."""
    
    def test_match_response_from_dict(self):
        """Test creating MatchResponse from dictionary."""
        match_dict = {
            "id": 1,
            "home_team": "Juventus",
            "away_team": "Inter Milan",
            "date": datetime.now(timezone.utc),
            "league": "Serie A",
            "status": "scheduled"
        }
        
        match = MatchResponse(**match_dict)
        
        assert match.id == 1
        assert match.home_team == "Juventus"
        assert match.away_team == "Inter Milan"
        assert match.league == "Serie A"
        assert match.status == "scheduled"


class TestMatchListResponse:
    """Test MatchListResponse schema."""
    
    def test_match_list_response(self):
        """Test creating a MatchListResponse."""
        matches_data = [
            {
                "id": 1,
                "home_team": "PSG",
                "away_team": "Olympique de Marseille",
                "date": datetime.now(timezone.utc),
                "league": "Ligue 1",
                "status": "scheduled"
            },
            {
                "id": 2,
                "home_team": "Barcelona",
                "away_team": "Real Madrid",
                "date": datetime.now(timezone.utc),
                "league": "La Liga",
                "status": "scheduled"
            }
        ]
        
        response = MatchListResponse(data=matches_data, count=2, meta={"page": 1})
        
        assert response.count == 2
        assert len(response.data) == 2
        assert response.meta["page"] == 1


class TestMatchStatsResponse:
    """Test MatchStatsResponse schema."""
    
    def test_match_stats_response(self):
        """Test creating a MatchStatsResponse."""
        stats = {
            "total_matches": 10,
            "matches_by_league": {"Ligue 1": 5, "La Liga": 5},
            "matches_by_status": {"scheduled": 5, "completed": 5},
            "upcoming_matches": 5,
            "completed_matches": 5
        }
        
        match_stats = MatchStatsResponse(**stats)
        
        assert match_stats.total_matches == 10
        assert match_stats.matches_by_league["Ligue 1"] == 5
        assert match_stats.matches_by_status["scheduled"] == 5
        assert match_stats.upcoming_matches == 5
        assert match_stats.completed_matches == 5
