# tests/unit/utils/test_vat.py
"""Tests for VAT calculation utilities."""

from decimal import Decimal

from app.utils.vat import (
    EU_VAT_RATES,
    VATRegime,
    calculate_vat_amount,
    determine_vat_regime,
    get_vat_rate_for_country,
    get_vat_rate_label,
    is_eu_country,
)


class TestGetVatRateForCountry:
    """Tests for get_vat_rate_for_country function."""

    def test_luxembourg_rate(self):
        """Luxembourg should have 17% VAT."""
        assert get_vat_rate_for_country("LU") == Decimal("17.00")

    def test_germany_rate(self):
        """Germany should have 19% VAT."""
        assert get_vat_rate_for_country("DE") == Decimal("19.00")

    def test_france_rate(self):
        """France should have 20% VAT."""
        assert get_vat_rate_for_country("FR") == Decimal("20.00")

    def test_hungary_rate(self):
        """Hungary should have 27% VAT (highest in EU)."""
        assert get_vat_rate_for_country("HU") == Decimal("27.00")

    def test_non_eu_country(self):
        """Non-EU countries should have 0% VAT."""
        assert get_vat_rate_for_country("US") == Decimal("0.00")
        assert get_vat_rate_for_country("CH") == Decimal("0.00")

    def test_lowercase_country_code(self):
        """Should handle lowercase country codes."""
        assert get_vat_rate_for_country("lu") == Decimal("17.00")

    def test_all_eu_countries_covered(self):
        """All 27 EU member states should be in the VAT rates."""
        assert len(EU_VAT_RATES) == 27


class TestIsEuCountry:
    """Tests for is_eu_country function."""

    def test_eu_countries(self):
        """EU countries should return True."""
        assert is_eu_country("LU") is True
        assert is_eu_country("DE") is True
        assert is_eu_country("FR") is True

    def test_non_eu_countries(self):
        """Non-EU countries should return False."""
        assert is_eu_country("US") is False
        assert is_eu_country("CH") is False
        assert is_eu_country("UK") is False


class TestGetVatRateLabel:
    """Tests for get_vat_rate_label function."""

    def test_luxembourg_label(self):
        """Luxembourg label should be formatted correctly."""
        label = get_vat_rate_label("LU", Decimal("17.00"))
        assert label == "Luxembourg VAT 17.00%"

    def test_germany_label(self):
        """Germany label should be formatted correctly."""
        label = get_vat_rate_label("DE", Decimal("19.00"))
        assert label == "Germany VAT 19.00%"


class TestDetermineVatRegime:
    """Tests for determine_vat_regime function."""

    def test_domestic_sale(self):
        """Same country should be domestic VAT."""
        result = determine_vat_regime(
            seller_country="LU",
            buyer_country="LU",
        )
        assert result.regime == VATRegime.DOMESTIC
        assert result.rate == Decimal("17.00")
        assert result.destination_country is None

    def test_domestic_sale_germany(self):
        """German domestic sale should use 19% VAT."""
        result = determine_vat_regime(
            seller_country="DE",
            buyer_country="DE",
        )
        assert result.regime == VATRegime.DOMESTIC
        assert result.rate == Decimal("19.00")

    def test_cross_border_b2b_reverse_charge(self):
        """B2B with VAT number should be reverse charge (0%)."""
        result = determine_vat_regime(
            seller_country="LU",
            buyer_country="DE",
            buyer_vat_number="DE123456789",
        )
        assert result.regime == VATRegime.REVERSE_CHARGE
        assert result.rate == Decimal("0.00")
        assert result.destination_country == "DE"
        assert result.label == "Reverse charge"

    def test_cross_border_b2c_with_oss(self):
        """B2C with OSS should use destination country VAT."""
        result = determine_vat_regime(
            seller_country="LU",
            buyer_country="DE",
            seller_oss_registered=True,
        )
        assert result.regime == VATRegime.OSS
        assert result.rate == Decimal("19.00")  # German VAT
        assert result.destination_country == "DE"

    def test_cross_border_b2c_without_oss(self):
        """B2C without OSS should use origin country VAT."""
        result = determine_vat_regime(
            seller_country="LU",
            buyer_country="DE",
            seller_oss_registered=False,
        )
        assert result.regime == VATRegime.ORIGIN
        assert result.rate == Decimal("17.00")  # Luxembourg VAT
        assert result.destination_country == "DE"

    def test_non_eu_sale(self):
        """Non-EU sales should be VAT exempt."""
        result = determine_vat_regime(
            seller_country="LU",
            buyer_country="US",
        )
        assert result.regime == VATRegime.EXEMPT
        assert result.rate == Decimal("0.00")
        assert result.destination_country == "US"

    def test_default_to_luxembourg(self):
        """Empty seller country should default to Luxembourg."""
        result = determine_vat_regime(
            seller_country="",
            buyer_country="LU",
        )
        assert result.regime == VATRegime.DOMESTIC
        assert result.rate == Decimal("17.00")


class TestCalculateVatAmount:
    """Tests for calculate_vat_amount function."""

    def test_standard_calculation(self):
        """Test standard VAT calculation."""
        # €100 at 17% = €17
        result = calculate_vat_amount(10000, Decimal("17.00"))
        assert result == 1700

    def test_zero_rate(self):
        """Zero rate should return 0."""
        result = calculate_vat_amount(10000, Decimal("0.00"))
        assert result == 0

    def test_negative_rate(self):
        """Negative rate should return 0."""
        result = calculate_vat_amount(10000, Decimal("-5.00"))
        assert result == 0

    def test_rounding(self):
        """Test proper rounding to cents."""
        # €33.33 at 19% = €6.3327, should round to €6.33 (633 cents)
        result = calculate_vat_amount(3333, Decimal("19.00"))
        assert result == 633

    def test_large_amount(self):
        """Test calculation with large amounts."""
        # €10,000 at 27% = €2,700
        result = calculate_vat_amount(1000000, Decimal("27.00"))
        assert result == 270000
