BerriAI/litellm · error · Exception
Error retrieving usage data: {e}
Error message
Error retrieving usage data: {e} What it means
Catch-all Exception from LiteLLMDatabase.get_usage_data wrapping the prisma query_raw call or the polars DataFrame construction. The message embeds the underlying error string, which can be a Prisma query error (bad parameter binding, SQL syntax from malformed timestamps), a Postgres connectivity error, or a polars schema-inference failure on the returned rows.
Source
Thrown at litellm/integrations/cloudzero/database.py:101
params: Final[list[Any]] = [
start_time_utc,
end_time_utc,
]
if limit is not None:
try:
params.append(int(limit))
except (TypeError, ValueError):
raise ValueError("limit must be an integer")
query += " LIMIT $3"
try:
db_response: Final = await client.db.query_raw(query, *params)
# Convert the response to polars DataFrame with full schema inference
# This prevents schema mismatch errors when data types vary across rows
return pl.DataFrame(db_response, infer_schema_length=None)
except Exception as e:
raise Exception(f"Error retrieving usage data: {e}")
View on GitHub (pinned to 6c2dcb801b)
Solutions
- Read the embedded error text — it distinguishes auth/connection ('password authentication failed', 'connection refused') from schema issues ('relation does not exist')
- Run prisma migration / let the proxy create tables by starting it once with the database connected before exporting
- Pass timezone-aware UTC datetimes for start_time_utc/end_time_utc
- Retry on transient connection errors with backoff; fix data/schema issues instead of retrying those
Example fix
# before
df = await db.get_usage_data(limit=100, start_time_utc="2026-01-01") # str not datetime
# after
from datetime import datetime, timezone
df = await db.get_usage_data(
limit=100,
start_time_utc=datetime(2026, 1, 1, tzinfo=timezone.utc),
) Defensive patterns
Strategy: retry
Validate before calling
from datetime import datetime
def valid_utc(dt) -> bool:
return dt is None or isinstance(dt, datetime) Type guard
from datetime import datetime
def is_valid_export_window(start, end) -> bool:
ok = (start is None or isinstance(start, datetime)) and (end is None or isinstance(end, datetime))
if isinstance(start, datetime) and isinstance(end, datetime):
ok = ok and start <= end
return ok Try / catch
import asyncio
async def export_with_retry(db, **kw):
for attempt in range(3):
try:
return await db.get_usage_data(**kw)
except Exception as e:
msg = str(e)
transient = any(s in msg for s in ("connection", "timeout", "terminating"))
if transient and attempt < 2:
await asyncio.sleep(2 ** attempt)
continue
raise Prevention
- Pass timezone-aware datetime objects, never strings
- Ensure the proxy has run migrations so spend tables exist before export
- Retry only transient DB errors; escalate schema errors immediately
When it happens
Trigger: Postgres unreachable or credentials rotated; start/end timestamps in a format Prisma cannot bind as $1/$2 parameters; the daily-user-spend table missing because the proxy schema was never migrated; polars failing infer_schema_length=None on inconsistent column types.
Common situations: Database credentials rotated without updating the proxy; running export against a fresh database with no spend table; passing tz-naive vs tz-aware datetimes inconsistently; very old rows with different column types breaking schema inference.
Related errors
- Database not connected. Connect a database to your proxy - h
- Error saving email settings to general_settings: {str(e)}
- Database not connected
- DB not connected. This endpoint needs a database; set DATABA
- DB not connected. This endpoint needs a database; set DATABA
AI-assisted analysis of BerriAI/litellm@6c2dcb801b (2026-08-15).
Data as JSON: /api/errors/5551befe9b2e8e5a.
Report an issue: GitHub.