From 8e4844c8ae5e2f01fb6577fa0923b1949e0c5cd2 Mon Sep 17 00:00:00 2001 From: b3nw Date: Mon, 16 Feb 2026 14:43:44 +0000 Subject: [PATCH] fix: condense 429 error logging and suppress litellm Provider List spam Issue 1: Gemini CLI 429 errors were dumping the full JSON error body across 20+ lines of console output. Now extracts key info (message, quotaResetDelay) into a single warning line. Full body still logged to transaction file. Issue 2: litellm prints 'Provider List: https://docs.litellm.ai/docs/providers' when custom OpenAI-compatible providers aren't in its known model list. Set litellm.suppress_debug_info = True to silence this. --- src/proxy_app/main.py | 1 + .../providers/gemini_cli_provider.py | 32 ++++++++++++++++--- 2 files changed, 29 insertions(+), 4 deletions(-) diff --git a/src/proxy_app/main.py b/src/proxy_app/main.py index 3e4bbbbc..22b9304f 100644 --- a/src/proxy_app/main.py +++ b/src/proxy_app/main.py @@ -627,6 +627,7 @@ async def process_credential(provider: str, path: str, provider_instance): os.environ["LITELLM_LOG"] = "ERROR" litellm.set_verbose = False + litellm.suppress_debug_info = True litellm.drop_params = True if USE_EMBEDDING_BATCHER: batcher = EmbeddingBatcher(client=client) diff --git a/src/rotator_library/providers/gemini_cli_provider.py b/src/rotator_library/providers/gemini_cli_provider.py index e8562a66..db475945 100644 --- a/src/rotator_library/providers/gemini_cli_provider.py +++ b/src/rotator_library/providers/gemini_cli_provider.py @@ -1530,12 +1530,36 @@ async def stream_handler(): if response.status_code >= 400: try: error_body = await response.aread() - lib_logger.error( - f"Gemini CLI API error {response.status_code}: {error_body.decode()}" - ) + error_text = error_body.decode() + # Always log full body to transaction file for debugging file_logger.log_error( - f"API error {response.status_code}: {error_body.decode()}" + f"API error {response.status_code}: {error_text}" ) + # Console logging: condensed for 429s, full for other errors + if response.status_code == 429: + # Extract key fields for a single-line summary + try: + err_json = json.loads(error_text) + err_msg = err_json.get("error", {}).get("message", "") + # Extract quotaResetDelay from details + reset_delay = "" + for detail in err_json.get("error", {}).get("details", []): + metadata = detail.get("metadata", {}) + if "quotaResetDelay" in metadata: + reset_delay = metadata["quotaResetDelay"] + break + summary = f"Gemini CLI 429: {err_msg}" + if reset_delay: + summary += f" (resetDelay: {reset_delay})" + lib_logger.warning(summary) + except (json.JSONDecodeError, KeyError): + lib_logger.warning( + f"Gemini CLI 429: {error_text[:200]}" + ) + else: + lib_logger.error( + f"Gemini CLI API error {response.status_code}: {error_text}" + ) except Exception: pass