BerriAI/litellm · error · ProxyException
tier_labels must be a JSON object of tier name to display na
Error message
tier_labels must be a JSON object of tier name to display name: {e} What it means
Input guard in _labeled_tiers_from_query: the tier_labels query parameter could not be parsed/validated as a JSON object of tier name to display name via ComplexityRouterConfig. The validators reject blank, duplicated, or canonical-name-stealing labels so the editor cannot prefill a rubric no router would accept; surfaced as a 400.
Source
Thrown at litellm/proxy/management_endpoints/model_management_endpoints.py:2208
)
def _labeled_tiers_from_query(tier_labels: str | None) -> tuple[tuple[ComplexityTier, str], ...] | None:
"""Resolve the tier_labels query param into the labeled tiers the rubric is built from.
Validated through ComplexityRouterConfig so the editor prefills what the router would send: the
same field validators that reject a blank, duplicated, or canonical-name-stealing label on the
write path reject it here, rather than this returning a rubric no router could be configured to
use. A malformed value is the caller's error, so it surfaces as a 400.
None when unset, letting classification_system_prompt apply its own default names.
"""
if not tier_labels:
return None
try:
return ComplexityRouterConfig(tier_labels=json.loads(tier_labels)).labeled_tiers()
except (JSONDecodeError, ValidationError) as e:
raise ProxyException(
message=f"tier_labels must be a JSON object of tier name to display name: {e}",
type=ProxyErrorTypes.bad_request_error,
code=status.HTTP_400_BAD_REQUEST,
param="tier_labels",
) from e
@router.get(
"/auto_router/classifier/default_prompt",
description="Get the built-in system prompt used by an auto-router's LLM classifier",
tags=["model management"], # mutable-ok: fastapi's decorator signature types tags as a list
dependencies=[Depends(user_api_key_auth)], # mutable-ok: fastapi's decorator signature types dependencies as a list
)
async def get_auto_router_classifier_default_prompt(
context_window_size: int = DEFAULT_CLASSIFIER_CONTEXT_WINDOW_SIZE,
tier_labels: str | None = None,
classification_rubric: ClassificationRubric | None = None,
) -> AutoRouterClassifierDefaultPromptResponse:View on GitHub (pinned to 77b7c6c40c)
Solutions
- Pass tier_labels as a JSON object mapping tier name to display name.
Defensive patterns
Strategy: validation
When it happens
Trigger: Thrown at litellm/proxy/management_endpoints/model_management_endpoints.py:2208 when the library encounters an invalid state.
Common situations: See trigger scenarios.
AI-assisted analysis of BerriAI/litellm@77b7c6c40c (2026-08-18).
Data as JSON: /api/errors/5aeadf9ff4410a34.
Report an issue: GitHub.