"""
CLM Repository Interfaces.

اینترفیس‌های ریپازیتوری — فقط تعریف (Abstract).
پیاده‌سازی در لایه infrastructure.
"""
from abc import ABC, abstractmethod
from datetime import date
from decimal import Decimal
from typing import Optional, List
from uuid import UUID

from shared.base_classes.repository import BaseRepository
from ..entities.contract import Contract
from ..entities.party import ContractParty
from ..entities.clause import ContractClause
from ..entities.milestone import ContractMilestone
from ..entities.amendment import ContractAmendment
from ..entities.template import ContractTemplate
from ..entities.renewal import ContractRenewal


class ContractRepository(BaseRepository[Contract]):
    """ریپازیتوری قرارداد."""

    @abstractmethod
    def get_by_number(self, tenant_id: UUID, contract_number: str) -> Optional[Contract]:
        """یافتن قرارداد با شماره."""
        pass

    @abstractmethod
    def find_expiring(self, tenant_id: UUID, days_ahead: int = 30) -> List[Contract]:
        """قراردادهایی که به‌زودی منقضی می‌شوند."""
        pass

    @abstractmethod
    def find_by_party(self, tenant_id: UUID, business_partner_id: UUID) -> List[Contract]:
        """قراردادهای مرتبط با یک طرف."""
        pass

    @abstractmethod
    def find_by_project(self, tenant_id: UUID, project_id: UUID) -> List[Contract]:
        """قراردادهای مرتبط با یک پروژه."""
        pass

    @abstractmethod
    def get_financial_summary(self, tenant_id: UUID, contract_id: UUID) -> dict:
        """خلاصه مالی قرارداد."""
        pass

    @abstractmethod
    def count_by_status(self, tenant_id: UUID) -> dict:
        """تعداد قراردادها به تفکیک وضعیت."""
        pass


class ContractPartyRepository(BaseRepository[ContractParty]):
    """ریپازیتوری طرف‌های قرارداد."""

    @abstractmethod
    def find_by_contract(self, contract_id: UUID) -> List[ContractParty]:
        pass


class ContractClauseRepository(BaseRepository[ContractClause]):
    """ریپازیتوری بندهای قرارداد."""

    @abstractmethod
    def find_by_contract(self, contract_id: UUID) -> List[ContractClause]:
        pass


class ContractMilestoneRepository(BaseRepository[ContractMilestone]):
    """ریپازیتوری مراحل قرارداد."""

    @abstractmethod
    def find_by_contract(self, contract_id: UUID) -> List[ContractMilestone]:
        pass

    @abstractmethod
    def find_overdue(self, tenant_id: UUID) -> List[ContractMilestone]:
        pass


class ContractAmendmentRepository(BaseRepository[ContractAmendment]):
    """ریپازیتوری الحاقیه‌ها."""

    @abstractmethod
    def find_by_contract(self, contract_id: UUID) -> List[ContractAmendment]:
        pass

    @abstractmethod
    def get_next_number(self, contract_id: UUID) -> int:
        pass


class ContractTemplateRepository(BaseRepository[ContractTemplate]):
    """ریپازیتوری قالب‌های قرارداد."""

    @abstractmethod
    def find_active(self, tenant_id: UUID) -> List[ContractTemplate]:
        pass

    @abstractmethod
    def get_default(self, tenant_id: UUID, contract_type: str) -> Optional[ContractTemplate]:
        pass


class ContractRenewalRepository(BaseRepository[ContractRenewal]):
    """ریپازیتوری تمدیدها."""

    @abstractmethod
    def find_by_contract(self, contract_id: UUID) -> List[ContractRenewal]:
        pass
