Unify backend logging configuration entrypoint

This commit is contained in:
ي
2026-03-12 15:05:30 +05:30
parent b410ece4ca
commit 51313f60dc
4 changed files with 64 additions and 16 deletions

View File

@@ -49,8 +49,8 @@ load_dotenv(project_root / '.env') # root .env (fallback)
load_dotenv() # CWD .env (fallback)
# Set up clean logging for end users
from logging_config import setup_clean_logging
setup_clean_logging()
from logging_config import configure_logging
configure_logging(mode="default", app_name="ALwrity")
# Import middleware
from middleware.auth_middleware import get_current_user

View File

@@ -9,13 +9,40 @@ import sys
from loguru import logger
def setup_clean_logging():
"""Set up clean logging for end users."""
verbose_mode = os.getenv("ALWRITY_VERBOSE", "false").lower() == "true"
# Always remove all existing handlers first to prevent conflicts
_LOGGING_CONFIGURED = False
class LoguruInterceptHandler(logging.Handler):
"""Forward stdlib logging records to Loguru."""
def emit(self, record: logging.LogRecord) -> None:
try:
level = logger.level(record.levelname).name
except ValueError:
level = record.levelno
frame, depth = logging.currentframe(), 2
while frame and frame.f_code.co_filename == logging.__file__:
frame = frame.f_back
depth += 1
logger.opt(depth=depth, exception=record.exc_info).log(level, record.getMessage())
def configure_logging(mode: str = "default", verbose: bool | None = None, app_name: str = "alwrity") -> bool:
"""Configure Loguru and stdlib logging into one shared pipeline."""
global _LOGGING_CONFIGURED
if verbose is None:
verbose_mode = mode == "verbose" or os.getenv("ALWRITY_VERBOSE", "false").lower() == "true"
else:
verbose_mode = verbose
if _LOGGING_CONFIGURED:
return verbose_mode
logger.remove()
if not verbose_mode:
# Suppress verbose logging for end users - be more aggressive
logging.getLogger('sqlalchemy.engine').setLevel(logging.CRITICAL)
@@ -90,7 +117,7 @@ def setup_clean_logging():
logger.add(
sys.stdout.write,
level="WARNING",
format="{time:HH:mm:ss} | {level: <8} | {name}:{function}:{line} - {message}\n",
format=f"{app_name} | {{time:HH:mm:ss}} | {{level: <8}} | {{name}}:{{function}}:{{line}} - {{message}}\n",
filter=warning_only_filter
)
# Add a focused sink to surface Story Video Generation INFO logs in console
@@ -108,7 +135,7 @@ def setup_clean_logging():
logger.add(
sys.stdout.write,
level="INFO",
format="{time:HH:mm:ss} | {level: <8} | {name}:{function}:{line} - {message}\n",
format=f"{app_name} | {{time:HH:mm:ss}} | {{level: <8}} | {{name}}:{{function}}:{{line}} - {{message}}\n",
filter=video_generation_filter
)
else:
@@ -116,12 +143,33 @@ def setup_clean_logging():
logger.add(
sys.stdout.write,
level="DEBUG",
format="{time:HH:mm:ss} | {level: <8} | {name}:{function}:{line} - {message}\n"
format=f"{app_name} | {{time:HH:mm:ss}} | {{level: <8}} | {{name}}:{{function}}:{{line}} - {{message}}\n"
)
intercept_handler = LoguruInterceptHandler()
root_logger = logging.getLogger()
root_logger.handlers = [intercept_handler]
root_logger.setLevel(logging.DEBUG if verbose_mode else logging.WARNING)
logging.captureWarnings(True)
warnings_logger = logging.getLogger("py.warnings")
warnings_logger.handlers = [intercept_handler]
warnings_logger.propagate = True
for existing_logger in logging.root.manager.loggerDict.values():
if isinstance(existing_logger, logging.Logger):
existing_logger.handlers = []
existing_logger.propagate = True
_LOGGING_CONFIGURED = True
return verbose_mode
def setup_clean_logging():
"""Backward-compatible wrapper for existing startup files."""
return configure_logging(mode="default")
def get_uvicorn_log_level():
"""Get appropriate uvicorn log level based on verbose mode."""
verbose_mode = os.getenv("ALWRITY_VERBOSE", "false").lower() == "true"

View File

@@ -49,8 +49,8 @@ load_dotenv(project_root / '.env') # root .env (fallback)
load_dotenv() # CWD .env (fallback)
# Set up clean logging for end users
from logging_config import setup_clean_logging
setup_clean_logging()
from logging_config import configure_logging
configure_logging(mode="default", app_name="ALwrity")
# Import middleware
from middleware.auth_middleware import get_current_user

View File

@@ -216,7 +216,7 @@ def start_backend(enable_reload=False, production_mode=False):
print("=" * 50)
# Set up clean logging for end users
from logging_config import setup_clean_logging, get_uvicorn_log_level
from logging_config import configure_logging, get_uvicorn_log_level
# Video stack preflight (diagnostics + version assert)
try:
from services.story_writer.video_preflight import (
@@ -228,7 +228,7 @@ def start_backend(enable_reload=False, production_mode=False):
log_video_stack_diagnostics = None
assert_supported_moviepy = None
verbose_mode = setup_clean_logging()
verbose_mode = configure_logging(mode="default", app_name="ALwrity")
uvicorn_log_level = get_uvicorn_log_level()
# Log diagnostics and assert versions (fail fast if misconfigured)