"""Auto-generated by adk-fluent generator. Manual edits will be overwritten."""

from __future__ import annotations
from collections import defaultdict
from typing import Any, Callable, Self
from adk_fluent._base import BuilderBase
from google.adk.apps.app import App as _ADK_App
from google.adk.runners import InMemoryRunner as _ADK_InMemoryRunner
from google.adk.runners import Runner as _ADK_Runner

# ======================================================================
# Builder: App
# ======================================================================

class App(BuilderBase):
    """Represents an LLM-backed agentic application."""

    # --- Class-level alias / field maps ---
    _ALIASES: dict[str, str] = {}
    _CALLBACK_ALIASES: dict[str, str] = {}
    _ADDITIVE_FIELDS: set[str] = set()


    def __init__(self, name: str, root_agent: str) -> None:
        self._config: dict[str, Any] = {"name": name, "root_agent": root_agent}
        self._callbacks: dict[str, list[Callable]] = defaultdict(list)
        self._lists: dict[str, list] = defaultdict(list)

    # --- Ergonomic aliases ---

    # --- Additive callback methods ---

    # --- Explicit field methods ---

    def plugins(self, value: list[BasePlugin]) -> Self:
        """Set the ``plugins`` field."""
        self._config["plugins"] = value
        return self


    def events_compaction_config(self, value: Union[EventsCompactionConfig, NoneType]) -> Self:
        """Set the ``events_compaction_config`` field."""
        self._config["events_compaction_config"] = value
        return self


    def context_cache_config(self, value: Union[ContextCacheConfig, NoneType]) -> Self:
        """Set the ``context_cache_config`` field."""
        self._config["context_cache_config"] = value
        return self


    def resumability_config(self, value: Union[ResumabilityConfig, NoneType]) -> Self:
        """Set the ``resumability_config`` field."""
        self._config["resumability_config"] = value
        return self

    # --- Extra methods ---

    # --- Dynamic field forwarding (safety net) ---

    def __getattr__(self, name: str):
        """Forward unknown methods to _ADK_App.model_fields for zero-maintenance compatibility."""
        if name.startswith("_"):
            raise AttributeError(name)

        # Resolve through alias map (class-level constants)
        _ALIASES = self.__class__._ALIASES
        _CALLBACK_ALIASES = self.__class__._CALLBACK_ALIASES
        _ADDITIVE_FIELDS = self.__class__._ADDITIVE_FIELDS

        field_name = _ALIASES.get(name, name)

        # Check if it's a callback alias
        if name in _CALLBACK_ALIASES:
            cb_field = _CALLBACK_ALIASES[name]
            def _cb_setter(fn: Callable) -> Self:
                self._callbacks[cb_field].append(fn)
                return self
            return _cb_setter

        # Validate against actual Pydantic schema
        if field_name not in _ADK_App.model_fields:
            available = sorted(
                set(_ADK_App.model_fields.keys())
                | set(_ALIASES.keys())
                | set(_CALLBACK_ALIASES.keys())
            )
            raise AttributeError(
                f"'{name}' is not a recognized field on _ADK_App. "
                f"Available: {', '.join(available)}"
            )

        # Return a setter that stores value and returns self for chaining
        def _setter(value: Any) -> Self:
            if field_name in _ADDITIVE_FIELDS:
                self._callbacks[field_name].append(value)
            else:
                self._config[field_name] = value
            return self

        return _setter

    # --- Terminal methods ---

    def build(self) -> _ADK_App:
        """Represents an LLM-backed agentic application. Resolve into a native ADK _ADK_App."""
        config = self._prepare_build_config()
        return _ADK_App(**config)


# ======================================================================
# Builder: InMemoryRunner
# ======================================================================

class InMemoryRunner(BuilderBase):
    """An in-memory Runner for testing and development."""

    # --- Class-level alias / field maps ---
    _ALIASES: dict[str, str] = {}
    _CALLBACK_ALIASES: dict[str, str] = {}
    _ADDITIVE_FIELDS: set[str] = set()
    _KNOWN_PARAMS: set[str] = {'app', 'agent', 'app_name', 'plugins', 'plugin_close_timeout'}


    def __init__(self, ) -> None:
        self._config: dict[str, Any] = {}
        self._callbacks: dict[str, list[Callable]] = defaultdict(list)
        self._lists: dict[str, list] = defaultdict(list)

    # --- Ergonomic aliases ---

    # --- Additive callback methods ---

    # --- Explicit field methods ---

    def agent(self, value: Optional[BaseAgent]) -> Self:
        """Set the ``agent`` field."""
        self._config["agent"] = value
        return self


    def app_name(self, value: Optional[str]) -> Self:
        """Set the ``app_name`` field."""
        self._config["app_name"] = value
        return self


    def plugins(self, value: Optional[list[BasePlugin]]) -> Self:
        """Set the ``plugins`` field."""
        self._config["plugins"] = value
        return self


    def app(self, value: Optional[App]) -> Self:
        """Set the ``app`` field."""
        self._config["app"] = value
        return self


    def plugin_close_timeout(self, value: float) -> Self:
        """Set the ``plugin_close_timeout`` field."""
        self._config["plugin_close_timeout"] = value
        return self

    # --- Extra methods ---

    # --- Dynamic field forwarding (safety net) ---

    def __getattr__(self, name: str):
        """Forward unknown methods to _ADK_InMemoryRunner init params for zero-maintenance compatibility."""
        if name.startswith("_"):
            raise AttributeError(name)

        # Resolve through alias map (class-level constants)
        _ALIASES = self.__class__._ALIASES
        _CALLBACK_ALIASES = self.__class__._CALLBACK_ALIASES
        _ADDITIVE_FIELDS = self.__class__._ADDITIVE_FIELDS
        _KNOWN_PARAMS = self.__class__._KNOWN_PARAMS

        field_name = _ALIASES.get(name, name)

        # Check if it's a callback alias
        if name in _CALLBACK_ALIASES:
            cb_field = _CALLBACK_ALIASES[name]
            def _cb_setter(fn: Callable) -> Self:
                self._callbacks[cb_field].append(fn)
                return self
            return _cb_setter

        # Validate against static _KNOWN_PARAMS set (non-Pydantic class)
        if field_name not in _KNOWN_PARAMS:
            available = sorted(
                _KNOWN_PARAMS
                | set(_ALIASES.keys())
                | set(_CALLBACK_ALIASES.keys())
            )
            raise AttributeError(
                f"'{name}' is not a recognized parameter on _ADK_InMemoryRunner. "
                f"Available: {', '.join(available)}"
            )

        # Return a setter that stores value and returns self for chaining
        def _setter(value: Any) -> Self:
            if field_name in _ADDITIVE_FIELDS:
                self._callbacks[field_name].append(value)
            else:
                self._config[field_name] = value
            return self

        return _setter

    # --- Terminal methods ---

    def build(self) -> _ADK_InMemoryRunner:
        """An in-memory Runner for testing and development. Resolve into a native ADK _ADK_InMemoryRunner."""
        config = self._prepare_build_config()
        return _ADK_InMemoryRunner(**config)


# ======================================================================
# Builder: Runner
# ======================================================================

class Runner(BuilderBase):
    """The Runner class is used to run agents."""

    # --- Class-level alias / field maps ---
    _ALIASES: dict[str, str] = {}
    _CALLBACK_ALIASES: dict[str, str] = {}
    _ADDITIVE_FIELDS: set[str] = set()
    _KNOWN_PARAMS: set[str] = {'app', 'session_service', 'agent', 'memory_service', 'auto_create_session', 'artifact_service', 'app_name', 'plugins', 'plugin_close_timeout', 'credential_service'}


    def __init__(self, session_service: str) -> None:
        self._config: dict[str, Any] = {"session_service": session_service}
        self._callbacks: dict[str, list[Callable]] = defaultdict(list)
        self._lists: dict[str, list] = defaultdict(list)

    # --- Ergonomic aliases ---

    # --- Additive callback methods ---

    # --- Explicit field methods ---

    def app(self, value: Optional[App]) -> Self:
        """Set the ``app`` field."""
        self._config["app"] = value
        return self


    def app_name(self, value: Optional[str]) -> Self:
        """Set the ``app_name`` field."""
        self._config["app_name"] = value
        return self


    def agent(self, value: Optional[BaseAgent]) -> Self:
        """Set the ``agent`` field."""
        self._config["agent"] = value
        return self


    def plugins(self, value: Optional[List[BasePlugin]]) -> Self:
        """Set the ``plugins`` field."""
        self._config["plugins"] = value
        return self


    def artifact_service(self, value: Optional[BaseArtifactService]) -> Self:
        """Set the ``artifact_service`` field."""
        self._config["artifact_service"] = value
        return self


    def memory_service(self, value: Optional[BaseMemoryService]) -> Self:
        """Set the ``memory_service`` field."""
        self._config["memory_service"] = value
        return self


    def credential_service(self, value: Optional[BaseCredentialService]) -> Self:
        """Set the ``credential_service`` field."""
        self._config["credential_service"] = value
        return self


    def plugin_close_timeout(self, value: float) -> Self:
        """Set the ``plugin_close_timeout`` field."""
        self._config["plugin_close_timeout"] = value
        return self


    def auto_create_session(self, value: bool) -> Self:
        """Set the ``auto_create_session`` field."""
        self._config["auto_create_session"] = value
        return self

    # --- Extra methods ---

    # --- Dynamic field forwarding (safety net) ---

    def __getattr__(self, name: str):
        """Forward unknown methods to _ADK_Runner init params for zero-maintenance compatibility."""
        if name.startswith("_"):
            raise AttributeError(name)

        # Resolve through alias map (class-level constants)
        _ALIASES = self.__class__._ALIASES
        _CALLBACK_ALIASES = self.__class__._CALLBACK_ALIASES
        _ADDITIVE_FIELDS = self.__class__._ADDITIVE_FIELDS
        _KNOWN_PARAMS = self.__class__._KNOWN_PARAMS

        field_name = _ALIASES.get(name, name)

        # Check if it's a callback alias
        if name in _CALLBACK_ALIASES:
            cb_field = _CALLBACK_ALIASES[name]
            def _cb_setter(fn: Callable) -> Self:
                self._callbacks[cb_field].append(fn)
                return self
            return _cb_setter

        # Validate against static _KNOWN_PARAMS set (non-Pydantic class)
        if field_name not in _KNOWN_PARAMS:
            available = sorted(
                _KNOWN_PARAMS
                | set(_ALIASES.keys())
                | set(_CALLBACK_ALIASES.keys())
            )
            raise AttributeError(
                f"'{name}' is not a recognized parameter on _ADK_Runner. "
                f"Available: {', '.join(available)}"
            )

        # Return a setter that stores value and returns self for chaining
        def _setter(value: Any) -> Self:
            if field_name in _ADDITIVE_FIELDS:
                self._callbacks[field_name].append(value)
            else:
                self._config[field_name] = value
            return self

        return _setter

    # --- Terminal methods ---

    def build(self) -> _ADK_Runner:
        """The Runner class is used to run agents. Resolve into a native ADK _ADK_Runner."""
        config = self._prepare_build_config()
        return _ADK_Runner(**config)
