"""
Logging configuration for Lattice.

Provides centralized logging setup with configurable log levels
via the LATTICE_LOG_LEVEL environment variable.

Usage:
    from lattice.logging_config import configure_logging

    configure_logging()  # Call once at application start

Levels (via LATTICE_LOG_LEVEL env var):
    DEBUG: Detailed diagnostic information
    INFO: General operational messages (default)
    WARNING: Warning conditions
    ERROR: Error conditions
"""

from __future__ import annotations

import logging
import os
import sys
from typing import Final

# Default log format
LOG_FORMAT: Final[str] = "%(asctime)s - %(name)s - %(levelname)s - %(message)s"
DATE_FORMAT: Final[str] = "%Y-%m-%d %H:%M:%S"

# Valid log levels
VALID_LEVELS: Final[dict[str, int]] = {
    "DEBUG": logging.DEBUG,
    "INFO": logging.INFO,
    "WARNING": logging.WARNING,
    "ERROR": logging.ERROR,
}


# @invar:allow shell_result: Log level lookup has sensible default, no error case
# @invar:allow shell_pure_logic: Environment read detected as pure, but is I/O
def get_log_level() -> int:
    """Get log level from LATTICE_LOG_LEVEL environment variable.

    Returns:
        Logging level integer (defaults to INFO).

    Example:
        >>> import os
        >>> os.environ["LATTICE_LOG_LEVEL"] = "DEBUG"
        >>> get_log_level() == 10  # logging.DEBUG
        True
        >>> del os.environ["LATTICE_LOG_LEVEL"]
        >>> get_log_level() == 20  # logging.INFO
        True
    """
    level_str = os.environ.get("LATTICE_LOG_LEVEL", "INFO").upper()
    return VALID_LEVELS.get(level_str, logging.INFO)


def configure_logging(level: int | None = None) -> None:
    """Configure logging for the Lattice package.

    Sets up a handler and formatter for the 'lattice' logger hierarchy.
    Safe to call multiple times (idempotent).

    Args:
        level: Optional log level override. If None, uses LATTICE_LOG_LEVEL
               environment variable or defaults to INFO.

    Example:
        >>> import logging
        >>> configure_logging(logging.DEBUG)
        >>> logger = logging.getLogger("lattice")
        >>> logger.level == logging.DEBUG
        True
    """
    if level is None:
        level = get_log_level()

    # Get the root lattice logger
    lattice_logger = logging.getLogger("lattice")

    # Only configure once (check if handler already exists)
    if lattice_logger.handlers:
        lattice_logger.setLevel(level)
        return

    lattice_logger.setLevel(level)

    # Create handler that writes to stderr
    handler = logging.StreamHandler(sys.stderr)
    handler.setLevel(level)

    # Create formatter
    formatter = logging.Formatter(LOG_FORMAT, datefmt=DATE_FORMAT)
    handler.setFormatter(formatter)

    # Add handler to logger
    lattice_logger.addHandler(handler)


# @invar:allow shell_result: Logger getter always succeeds, no error case
def get_logger(name: str) -> logging.Logger:
    """Get a logger within the Lattice namespace.

    Args:
        name: Module name (typically __name__).

    Returns:
        Configured logger instance.

    Example:
        >>> logger = get_logger("lattice.shell.cli")
        >>> logger.name
        'lattice.shell.cli'
    """
    return logging.getLogger(name)
