83 lines
3.3 KiB
Python
83 lines
3.3 KiB
Python
"""
|
|
Debug utilities for COCO Tools with simple/verbose logging control.
|
|
"""
|
|
import logging
|
|
from typing import List, Dict, Any, Optional
|
|
|
|
# Global debug mode control - default to simple
|
|
DEBUG_MODE = "simple" # "simple" or "verbose"
|
|
|
|
# Flag to prevent multiple logging configurations
|
|
_LOGGING_CONFIGURED = False
|
|
|
|
def setup_logging(level: int = logging.INFO):
|
|
"""
|
|
Centralized logging configuration for all COCO Tools modules.
|
|
Should be called once at module level to avoid conflicts.
|
|
"""
|
|
global _LOGGING_CONFIGURED
|
|
if not _LOGGING_CONFIGURED:
|
|
# Check if root logger already has handlers to prevent duplicate setup
|
|
if not logging.getLogger().handlers:
|
|
logging.basicConfig(level=level)
|
|
_LOGGING_CONFIGURED = True
|
|
|
|
def set_debug_mode(mode: str):
|
|
"""Set global debug mode"""
|
|
global DEBUG_MODE
|
|
DEBUG_MODE = mode.lower() if mode.lower() in ["simple", "verbose"] else "simple"
|
|
|
|
def get_debug_mode() -> str:
|
|
"""Get current debug mode"""
|
|
return DEBUG_MODE
|
|
|
|
def debug_log(logger: logging.Logger, level: str, simple_msg: str, verbose_msg: Optional[str] = None, **kwargs):
|
|
"""
|
|
Log with debug verbosity control.
|
|
|
|
Args:
|
|
logger: Logger instance
|
|
level: Log level ("info", "warning", "error", "debug")
|
|
simple_msg: Short message for simple mode
|
|
verbose_msg: Detailed message for verbose mode (if None, uses simple_msg)
|
|
**kwargs: Additional context for verbose mode
|
|
"""
|
|
message = simple_msg if DEBUG_MODE == "simple" else (verbose_msg or simple_msg)
|
|
|
|
# Add context info in verbose mode
|
|
if DEBUG_MODE == "verbose" and kwargs:
|
|
context_parts = [f"{k}={v}" for k, v in kwargs.items()]
|
|
message += f" [{', '.join(context_parts)}]"
|
|
|
|
# Log based on level
|
|
if level.lower() == "info":
|
|
logger.info(message)
|
|
elif level.lower() == "warning":
|
|
logger.warning(message)
|
|
elif level.lower() == "error":
|
|
logger.error(message)
|
|
elif level.lower() == "debug":
|
|
logger.debug(message)
|
|
|
|
def format_layer_names(layer_names: List[str], max_simple: int = None) -> str:
|
|
"""Format layer names for logging - show all layer names as they're important for users"""
|
|
# Always show all layer names as users need to know what's available
|
|
return ', '.join(layer_names)
|
|
|
|
def format_tensor_info(tensor_shape: tuple, tensor_dtype: Any, name: str = "") -> str:
|
|
"""Format tensor information for logging"""
|
|
if DEBUG_MODE == "simple":
|
|
return f"{name} shape={tensor_shape}" if name else f"shape={tensor_shape}"
|
|
return f"{name} shape={tensor_shape}, dtype={tensor_dtype}" if name else f"shape={tensor_shape}, dtype={tensor_dtype}"
|
|
|
|
def create_fallback_functions():
|
|
"""
|
|
Create fallback functions for cases where debug_utils import fails.
|
|
Returns a dictionary of fallback functions following single responsibility principle.
|
|
"""
|
|
return {
|
|
'debug_log': lambda logger, level, simple_msg, verbose_msg=None, **kwargs: getattr(logger, level.lower())(simple_msg),
|
|
'format_layer_names': lambda layer_names, max_simple=None: ', '.join(layer_names),
|
|
'format_tensor_info': lambda tensor_shape, tensor_dtype, name="": f"{name} shape={tensor_shape}" if name else f"shape={tensor_shape}",
|
|
'generate_preview_for_comfyui': lambda image_tensor, source_path="", is_sequence=False, frame_index=0: None
|
|
} |