"""
Auto-Discovery Utilities

Provides utility functions for auto-discovering and importing modules
to trigger decorator-based registration.

Usage:
    from libs.sixtysix_core.registry import discover_modules

    # In strategies/__init__.py
    discover_modules(__name__, __path__[0], exclude=['base'])
"""

import importlib
import pkgutil
from typing import List, Optional, Set


def discover_modules(
    package_name: str,
    package_path: str,
    exclude: Optional[List[str]] = None,
    recursive: bool = True
) -> Set[str]:
    """
    Auto-discover and import all modules in a package.

    This triggers any decorator-based registration (like @strategy, @indicator)
    by importing the modules.

    Args:
        package_name: The package's __name__ (e.g., 'application.analysis.strategies')
        package_path: The package's directory path (__path__[0])
        exclude: List of module names to skip (e.g., ['base', 'test'])
        recursive: Whether to recurse into subpackages (default: True)

    Returns:
        Set of imported module names

    Example:
        # In strategies/__init__.py
        from libs.sixtysix_core.registry import discover_modules

        discover_modules(
            __name__,
            __path__[0],
            exclude=['base']
        )
    """
    exclude_set = set(exclude or [])
    exclude_set.add('__pycache__')

    imported = set()

    if recursive:
        # Walk all subpackages
        for importer, module_name, is_pkg in pkgutil.walk_packages(
            [package_path],
            prefix=f"{package_name}."
        ):
            # Get the last part of the module name
            module_basename = module_name.split('.')[-1]

            # Skip excluded modules and private modules
            if module_basename.startswith('_') or module_basename in exclude_set:
                continue

            try:
                importlib.import_module(module_name)
                imported.add(module_name)
            except Exception:
                # Skip modules that fail to import
                # (could be missing dependencies, syntax errors, etc.)
                pass
    else:
        # Only top-level modules
        for importer, module_name, is_pkg in pkgutil.iter_modules([package_path]):
            if module_name.startswith('_') or module_name in exclude_set:
                continue

            full_name = f"{package_name}.{module_name}"
            try:
                importlib.import_module(full_name)
                imported.add(full_name)
            except Exception:
                pass

    return imported


__all__ = ['discover_modules']
