litellm - ✅(Solved) Fix [Bug]: Sessions are no longer correctly grouped together in the Spend Logs UI [1 pull requests, 1 comments, 2 participants]

Official PRs (…)
ON THIS PAGE

Recommended Tools

×6

Utilities matched from this issue’s tags and category — try them while you read without losing context.

GitHub issue graph ai analysis

Paste a GitHub issue URL. We fetch that issue, discover linked issues from bodies/comments/timeline, collect linked pull requests, and produce a structured English report.

The report is written in English Markdown for sharing and archival.

Helpful · Quick feedback

Loading…
GitHub stats
BerriAI/litellm#23157Fetched 2026-04-08 00:38:15
View on GitHub
Comments
1
Participants
2
Timeline
9
Reactions
0
Author
Participants
Timeline (top)
labeled ×3mentioned ×2subscribed ×2commented ×1

Fix Action

Fixed

PR fix notes

PR #23245: fix: session grouping in Spend Logs UI for query_raw dict rows

Description (problem / solution / changelog)

fix : #23157

relevant issues

  • Fixes Spend Logs session grouping.

Pre-Submission checklist

  • Please complete all items before asking a LiteLLM maintainer to review your PR [ ] I have Added testing in the directory, Adding at least 1 test is a hard requirement - see details [ ] My PR passes all unit tests on [ ] 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.

Type

🐛 Bug Fix

Changes

  • Fix session grouping.
  • Fix session_total_count.
  • Add test.

Changed files

  • litellm/proxy/spend_tracking/spend_management_endpoints.py (modified, +27/-12)

Code Example

export LITELLM_URL=http://localhost:4000
export LITELLM_KEY=someKey
export MODEL="openrouter/google/gemini-3-flash-preview" # use any configured model
export SESSION_ID="repro-session-123"

for i in 1 2 3; do
  curl -sS "$LITELLM_URL/chat/completions" \
    -H "Authorization: Bearer $LITELLM_KEY" \
    -H "Content-Type: application/json" \
    -d "{
      \"model\": \"$MODEL\",
      \"messages\": [{\"role\": \"user\", \"content\": \"repro $i\"}],
      \"litellm_session_id\": \"$SESSION_ID\"
    }" > /dev/null
done

---

curl -sS \
  -H "Authorization: Bearer $LITELLM_KEY" \
  "$LITELLM_URL/spend/logs/session/ui?session_id=$SESSION_ID" | jq

---

curl -sS \
  -H "Authorization: Bearer $LITELLM_KEY" \
  "$LITELLM_URL/spend/logs/ui?start_date=2026-03-09%2000:00:00&end_date=2026-03-10%2000:00:00&page=1&page_size=50" \
  | jq '.data | map(select(.session_id == "repro-session-123")) | map({request_id, session_id, session_total_count})'
RAW_BUFFERClick to expand / collapse

Check for existing issues

  • I have searched the existing issues and checked that my issue is not a duplicate.

What happened?

<img width="576" height="148" alt="Image" src="https://github.com/user-attachments/assets/ef2a450d-ee96-4af9-a2f5-403923e8a3ff" />

The above all have the exact same sessionId - chat-preview:c896735d087144350aa43c8b2da0deca9 but whenever you click on the session:

<img width="233" height="531" alt="Image" src="https://github.com/user-attachments/assets/3a9b1f83-4726-4981-ac7d-495075c60b4f" />

They are not grouped at all.

Looks like this was introduced in https://github.com/BerriAI/litellm/pull/21018 by @ishaan-jaff ( incredible work on this product btw, if you read this!! )

Steps to Reproduce (Codex put this together, but I did verify manually that it repro'd)

Repro Steps

Environment:

LiteLLM version with bug: v1.81.12-stable.1 Working comparison: 1.80.15-stable.1 Observed on POST /chat/completions and the Logs UI / /spend/logs/ui Start LiteLLM v1.81.12-stable.1 with spend logging enabled and a DB attached.

Send 3 chat completion requests with the same litellm_session_id.

export LITELLM_URL=http://localhost:4000
export LITELLM_KEY=someKey
export MODEL="openrouter/google/gemini-3-flash-preview" # use any configured model
export SESSION_ID="repro-session-123"

for i in 1 2 3; do
  curl -sS "$LITELLM_URL/chat/completions" \
    -H "Authorization: Bearer $LITELLM_KEY" \
    -H "Content-Type: application/json" \
    -d "{
      \"model\": \"$MODEL\",
      \"messages\": [{\"role\": \"user\", \"content\": \"repro $i\"}],
      \"litellm_session_id\": \"$SESSION_ID\"
    }" > /dev/null
done

Confirm the dedicated session endpoint returns all 3 rows.

curl -sS \
  -H "Authorization: Bearer $LITELLM_KEY" \
  "$LITELLM_URL/spend/logs/session/ui?session_id=$SESSION_ID" | jq

Expected result: total = 3 data contains all 3 requests

Now fetch the normal logs list endpoint for a time range that includes those requests.

curl -sS \
  -H "Authorization: Bearer $LITELLM_KEY" \
  "$LITELLM_URL/spend/logs/ui?start_date=2026-03-09%2000:00:00&end_date=2026-03-10%2000:00:00&page=1&page_size=50" \
  | jq '.data | map(select(.session_id == "repro-session-123")) | map({request_id, session_id, session_total_count})'

Actual result on v1.81.12-stable.1:

all matching rows have session_total_count: 1 Expected result:

  • Each matching row should have session_total_count: 3
  • the Logs UI should treat them as one grouped session

Open the Logs UI and click the session column for one of those rows. Actual: rows are not grouped as a multi-request session Expected: they should open as one grouped session

What part of LiteLLM is this about?

UI Dashboard

What LiteLLM version are you on ?

v1.80.15-stable.1

extent analysis

Fix Plan

To resolve the issue of session grouping in the Logs UI, we need to update the logic for calculating session_total_count and grouping sessions.

Here are the steps:

  • Update the database query to correctly calculate session_total_count for each session.
  • Modify the Logs UI to group sessions based on the session_id.
  • Ensure that the session_id is correctly passed and used in the API requests.

Code Changes

# Update the database query to calculate session_total_count
def get_session_total_count(session_id):
    # Assuming a database connection is established
    query = "SELECT COUNT(*) FROM logs WHERE session_id = %s"
    cursor.execute(query, (session_id,))
    return cursor.fetchone()[0]

# Modify the Logs UI to group sessions
def get_grouped_sessions(logs):
    grouped_sessions = {}
    for log in logs:
        session_id = log['session_id']
        if session_id not in grouped_sessions:
            grouped_sessions[session_id] = []
        grouped_sessions[session_id].append(log)
    return grouped_sessions

# Ensure correct session_id usage in API requests
def get_logs(session_id):
    # Use the session_id to fetch logs
    query = "SELECT * FROM logs WHERE session_id = %s"
    cursor.execute(query, (session_id,))
    return cursor.fetchall()

Verification

To verify the fix, follow these steps:

  • Send multiple chat completion requests with the same litellm_session_id.
  • Check the dedicated session endpoint to ensure all requests are returned.
  • Fetch the normal logs list endpoint for a time range that includes those requests.
  • Verify that each matching row has the correct session_total_count.
  • Open the Logs UI and click the session column for one of those rows to ensure they are grouped correctly.

Extra Tips

  • Ensure that the database connection is stable and queries are optimized for performance.
  • Consider adding logging and error handling to the updated code to improve debugging and user experience.
  • Test the fix thoroughly to ensure it resolves the issue without introducing new problems.

Vote matrix · Quick signals

Works
Did the solution work? Tap to confirm.
Easy Fix
Was it a quick fix?
Time Saver
Did it save you time?
Blocking
Was it severely blocking?
Common Issue
Are others likely hitting this too?
Flaky / Intermittent
Is it intermittent?
Verified / Reproducible
Can you reproduce it reliably?
Loading…

Still need to ship something?

×6

Another batch ranked right after the header list — different links, same matching logic.

Back to top recommendations

TRENDING