From 3e2ce49b0d22e91da0e357cff4d1b53c1f0f5667 Mon Sep 17 00:00:00 2001 From: Alexsander Hamir Date: Sat, 24 Jan 2026 09:36:53 -0800 Subject: [PATCH] fix: eliminate JSON logging duplication in litellm-proxy-extras - Integrate litellm_proxy_extras logger with global JSON logging setting - Prevent log propagation to avoid duplicate text/JSON output - Use consistent JSON format when json_logs is enabled - Simplify logging implementation for maintainability Fixes issue where proxy startup logs appeared twice (text + JSON) when json_logs: true was configured. --- .../litellm_proxy_extras/_logging.py | 42 ++++++++++++++++--- 1 file changed, 36 insertions(+), 6 deletions(-) diff --git a/litellm-proxy-extras/litellm_proxy_extras/_logging.py b/litellm-proxy-extras/litellm_proxy_extras/_logging.py index 118caecf488..256be29c832 100644 --- a/litellm-proxy-extras/litellm_proxy_extras/_logging.py +++ b/litellm-proxy-extras/litellm_proxy_extras/_logging.py @@ -1,12 +1,42 @@ +import json import logging +import os +from datetime import datetime + + +class JsonFormatter(logging.Formatter): + def formatTime(self, record, datefmt=None): + dt = datetime.fromtimestamp(record.created) + return dt.isoformat() + + def format(self, record): + json_record = { + "message": record.getMessage(), + "level": record.levelname, + "timestamp": self.formatTime(record), + } + if record.exc_info: + json_record["stacktrace"] = self.formatException(record.exc_info) + return json.dumps(json_record) + + +def _is_json_enabled(): + try: + import litellm + return getattr(litellm, 'json_logs', False) + except (ImportError, AttributeError): + return os.getenv("JSON_LOGS", "false").lower() == "true" + -# Set up package logger logger = logging.getLogger("litellm_proxy_extras") -if not logger.handlers: # Only add handler if none exists + +if not logger.handlers: handler = logging.StreamHandler() - formatter = logging.Formatter( - "%(asctime)s - %(name)s - %(levelname)s - %(message)s" - ) - handler.setFormatter(formatter) + if _is_json_enabled(): + handler.setFormatter(JsonFormatter()) + else: + handler.setFormatter(logging.Formatter("%(asctime)s - %(name)s - %(levelname)s - %(message)s")) logger.addHandler(handler) logger.setLevel(logging.INFO) + +logger.propagate = False