Skip to content

[Fix] Redact JWT bearer tokens in debug logs#22314

Open
shivamrawat1 wants to merge 2 commits intomainfrom
litellm_remove_jwts
Open

[Fix] Redact JWT bearer tokens in debug logs#22314
shivamrawat1 wants to merge 2 commits intomainfrom
litellm_remove_jwts

Conversation

@shivamrawat1
Copy link
Collaborator

@shivamrawat1 shivamrawat1 commented Feb 27, 2026

Relevant issues

With --detailed_debug, JWT bearer tokens from the Authorization header were logged in full. This exposed credentials in server output, log files, and any log aggregation systems.

The proxy stores raw request headers (including Authorization) in data["secret_fields"] for MCP and response forwarding. Several debug log calls (e.g. print_args_passed_to_litellm in utils.py and the "receiving data" logs in litellm_pre_call_utils.py and proxy_server.py) logged the full data or kwargs without redacting these fields.
Screenshot 2026-02-27 at 1 17 32 PM

Pre-Submission checklist

Please complete all items before asking a LiteLLM maintainer to review your PR

  • I have Added testing in the tests/litellm/ directory, Adding at least 1 test is a hard requirement - see details
  • My PR passes all unit tests on make test-unit
  • My PR's scope is as isolated as possible, it only solves 1 specific problem
  • I have requested a Greptile review by commenting @greptileai and received a Confidence Score of at least 4/5 before requesting a maintainer review

CI (LiteLLM team)

CI status guideline:

  • 50-55 passing tests: main is stable with minor issues.
  • 45-49 passing tests: acceptable but needs attention
  • <= 40 passing tests: unstable; be careful with your merges and assess the risk.
  • Branch creation CI run
    Link:

  • CI run for the last commit
    Link:

  • Merge / cherry-pick CI run
    Links:

Type

🐛 Bug Fix
✅ Test

Changes

A SensitiveLogFilter was added in litellm/_logging.py and attached to all three LiteLLM loggers. It runs before any handler and redacts Bearer tokens in the formatted log message using a regex, replacing them with Bearer [REDACTED]. This centralizes redaction so new log sites are covered without per-call changes.

@vercel
Copy link

vercel bot commented Feb 27, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
litellm Ready Ready Preview, Comment Feb 27, 2026 9:04pm

Request Review

@greptile-apps
Copy link
Contributor

greptile-apps bot commented Feb 27, 2026

Greptile Summary

This PR adds a SensitiveLogFilter to litellm/_logging.py that uses a compiled regex to redact Bearer tokens (JWTs, API keys) from all log output before it reaches handlers. The filter is attached to all three named LiteLLM loggers and the root logger, providing centralized defense-in-depth redaction.

  • Adds SensitiveLogFilter class that intercepts log records, pre-formats the message, and applies regex substitution to replace Bearer tokens with Bearer [REDACTED]
  • Compiles the regex pattern at module level for performance (_BEARER_TOKEN_PATTERN)
  • Adds 10 well-structured unit tests covering plain messages, dict format args, case insensitivity, multiple tokens per message, and edge cases
  • The filter correctly survives logger reinitialization (e.g., when _turn_on_json() is called) since Python's logging separates filters from handlers
  • Note: print_verbose() functions that use raw print() (not the logging system) are not covered by this filter — a broader scope concern for future work

Confidence Score: 4/5

  • This PR is safe to merge — it adds a non-breaking logging filter with good test coverage and no functional side effects.
  • Score of 4 reflects a well-scoped security fix with comprehensive tests. Deducted one point for the bare except Exception: pass which could silently allow tokens through if log formatting fails — a concern for a security-critical feature.
  • litellm/_logging.py — review the exception handling in the filter's filter() method to ensure redaction failures are surfaced.

Important Files Changed

Filename Overview
litellm/_logging.py Adds SensitiveLogFilter class and regex to redact Bearer tokens from log messages. Filter correctly attached to all named loggers and root logger. One concern: bare except could silently skip redaction on format errors.
tests/test_litellm/test_logging.py Comprehensive unit tests for SensitiveLogFilter covering plain messages, dict format args, case insensitivity, multiple tokens, edge cases, and arg clearing. All tests are properly mocked with no network calls.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart TD
    A["Log call: verbose_logger.debug(msg, args)"] --> B["SensitiveLogFilter.filter()"]
    B --> C{"record.getMessage()\nsucceeds?"}
    C -->|Yes| D{"Bearer token\nfound in message?"}
    C -->|No| H["except: pass\n(token may leak)"]
    D -->|Yes| E["Regex sub: Bearer [REDACTED]"]
    E --> F["record.args = None"]
    D -->|No| G["Record unchanged"]
    F --> I["return True → Handler/Formatter"]
    G --> I
    H --> I
Loading

Last reviewed commit: 193fe54

Copy link
Contributor

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

2 files reviewed, 2 comments

Edit Code Review Agent Settings | Greptile

@shivamrawat1
Copy link
Collaborator Author

@greptile re-review now that we have added the sensitive filter in the root logger as asked with the new commit

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant