"""
FernHub - רכז תקשורת בין-בוטים
"""

from typing import Dict, List, Callable, Any
import asyncio
from collections import defaultdict
import logging

logger = logging.getLogger(__name__)


class פרנהאב:
    """
    מרכז pub-sub פשוט לתקשורת בין בוטים.
    """

    def __init__(self):
        self._מנויים: Dict[str, List[Callable]] = defaultdict(list)
        self._subscribers = self._מנויים  # תאימות אנגלית
        self._לולאת_אירועים = None
        self._event_loop = self._לולאת_אירועים  # תאימות אנגלית

    def הירשם(self, סוג_אירוע: str, קריאה: Callable):
        """
        הרשמה לסוג אירוע.
        """
        self._מנויים[סוג_אירוע].append(קריאה)

    def בטל_הרשמה(self, סוג_אירוע: str, קריאה: Callable):
        """
        ביטול הרשמה לסוג אירוע.
        """
        if סוג_אירוע in self._מנויים:
            try:
                self._מנויים[סוג_אירוע].remove(קריאה)
            except ValueError:
                pass

    def פרסם(self, סוג_אירוע: str, נתוני_אירוע: Dict[str, Any]):
        """
        פרסום אירוע לכל המנויים.
        """
        if סוג_אירוע in self._מנויים:
            for קריאה in self._מנויים[סוג_אירוע]:
                try:
                    if self._לולאת_אירועים and asyncio.iscoroutinefunction(קריאה):
                        asyncio.run_coroutine_threadsafe(קריאה(נתוני_אירוע), self._לולאת_אירועים)
                    else:
                        קריאה(נתוני_אירוע)
                except Exception:
                    logger.exception("[FernHub] Error in callback for %s", סוג_אירוע)

    def קבע_לולאת_אירועים(self, לולאה: asyncio.AbstractEventLoop):
        """
        הגדרת לולאת אירועים עבור קריאות אסינכרוניות.
        """
        self._לולאת_אירועים = לולאה
        self._event_loop = לולאה

    # --- תאימות אנגלית ---
    subscribe = הירשם
    unsubscribe = בטל_הרשמה
    publish = פרסם
    set_event_loop = קבע_לולאת_אירועים


# תאימות שמות
FernHub = פרנהאב
