Commit graph

4703 commits

Author SHA1 Message Date
yuneng-jiang
44c3b4bc55 [Feature] UI: Add New badges for Projects discoverability
- Settings leftnav item: "New" badge
- Admin Settings leftnav item: dot badge
- UI Settings tab in Admin Panel: "New" badge

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-28 10:32:02 -08:00
yuneng-jiang
e325db35a3 [Fix] Add useUISettings mock to KeyInfoView test
The test was failing with "No QueryClient set" after useUISettings was
added to key_info_view.tsx. Mock the hook to avoid the dependency.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-28 10:32:02 -08:00
yuneng-jiang
2abe2901c6 [Feature] UI - Admin Settings: Add opt-in flag for Projects feature
Add `enable_projects_ui` toggle in Admin Settings so admins can opt
into the beta Projects feature. When disabled (default), the Projects
page is hidden from the sidebar and the project field is hidden in
the create key flow and key settings views.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-28 10:32:02 -08:00
yuneng-jiang
2285dc78b9 [Fix] UI - resolve flaky tests from leaked @tremor/react Tooltip timer
Local vi.mock("@tremor/react") overrides in router_settings tests were
clobbering the global setupTests.ts mock, re-introducing the real Tooltip
component which schedules a setTimeout. When jsdom tears down after each
test file, the pending timer fires and hits window is not defined, which
Vitest flags as an unhandled error that can cause false positive failures
in subsequent tests (including the create_mcp_server timeout in CI).

Fix: add Switch to the global @tremor/react mock in setupTests.ts (the
only reason the local overrides existed), then remove the three local
vi.mock("@tremor/react") blocks so all test files inherit the global mock
with properly stubbed Button, Tooltip, and Switch.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-28 10:28:27 -08:00
yuneng-jiang
3e37f44789
Merge pull request #22412 from BerriAI/litellm_ui_project_delete
[Feature] UI - Projects: Add delete project action
2026-02-28 10:17:34 -08:00
Ishaan Jaff
29e3fd5d79
[Release Fix] (#22411)
* fix(lint): suppress PLR0915 for 3 complex methods that exceed 50-statement limit

- streaming_iterator.py: _process_event (84 statements)
- transformation.py: translate_messages_to_responses_input (51 statements)
- transformation.py: transform_realtime_response (54 statements)

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(mypy): resolve type errors in public_endpoints, user_api_key_auth, common_utils, transformation

- public_endpoints.py: fix _cached_endpoints type annotation
- user_api_key_auth.py: accept Optional[str] for end_user_id parameter
- common_utils.py: add NewProjectRequest/UpdateProjectRequest to Union type
- transformation.py: add ChatCompletionRedactedThinkingBlock and list[Any] to content type

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(proxy-extras): bump version to 0.4.50 and sync schema

- Bump litellm-proxy-extras from 0.4.49 to 0.4.50
- Sync schema.prisma with main proxy schema
- Includes new LiteLLM_ClaudeCodePluginTable model
- Includes new @@index([startTime, request_id]) on SpendLogs
- Update version references in requirements.txt and pyproject.toml

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(router): use string id in test_add_deployment and add defensive str() in register_model

- Change test to use string '100' instead of int 100 for model_info.id
- Add str() conversion in register_model to prevent AttributeError on non-string keys

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(security): update minimatch to 10.2.4 to fix CVE-2026-27903 and CVE-2026-27904

- Run npm audit fix in docs/my-website
- Updates minimatch from 10.2.1 to 10.2.4 (fixes HIGH severity ReDoS vulnerabilities)

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): update realtime guardrail test assertions to match actual guardrail behavior

- test_text_message_blocked_by_guardrail_no_ai_response: allow guardrail's own block
  message text in response.done (previously expected empty content)
- test_voice_transcript_blocked_by_guardrail: allow guardrail to send response.cancel
  + block message + response.create flow (previously expected no response.create)

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: revert proxy-extras version in requirements.txt and pyproject.toml

The litellm-proxy-extras 0.4.50 is not published to PyPI yet, so consumer
references must stay at 0.4.49. Only the source package pyproject.toml
should be bumped to 0.4.50 for the publish_proxy_extras CI job.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: make transcript delta check optional in voice guardrail test

The guardrail sends an error event (guardrail_violation) when blocking
voice transcripts; it does not always produce transcript deltas. Remove
the assertion requiring response.audio_transcript.delta since the error
event is the primary signal that blocked content was handled.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* Add missing env keys to documentation: LITELLM_MAX_STREAMING_DURATION_SECONDS and LITELLM_USE_CHAT_COMPLETIONS_URL_FOR_ANTHROPIC_MESSAGES

These two environment variables were used in code but not documented in the
environment variables reference section of config_settings.md, causing the
test_env_keys.py CI test to fail.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* Fix 13 mypy type errors across 6 files

- in_flight_requests_middleware.py: Fix type: ignore error codes from
  [union-attr] to [attr-defined], add [arg-type] for Gauge **kwargs
- transformation.py: Add [assignment] ignore for output_format reassignment,
  add fallback empty string for tool use id to fix arg-type
- responses/main.py: Remove redundant type annotation on second
  secret_fields assignment to fix no-redef
- streaming_iterator.py: Add [assignment] ignores for intermediate
  cache token assignments
- handler.py: Add [typeddict-item] ignore for AnthropicMessagesRequest
  construction from dict
- public_endpoints.py: Add [arg-type] ignore for _load_endpoints()
  return type mismatch with SupportedEndpoint model

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: add auth overrides to spend tracking tests, fix realtime guardrail assertion, update UI minimatch

- Add app.dependency_overrides for user_api_key_auth in 4 spend tracking tests
  that were returning 401 Unauthorized (error_code, error_message,
  error_code_and_key_alias, key_hash)
- Fix realtime guardrail test to check ANY error event for guardrail_violation
  instead of just the first (OpenAI may send its own errors first)
- Update ui/litellm-dashboard/package-lock.json to fix minimatch vulnerability

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* Fix failing MCP e2e and create_mcp_server UI tests

Test 1 (test_independent_clients_no_shared_session):
- Add allow_all_keys: true to MCP servers in test config. With master_key
  and no DB, get_allowed_mcp_servers returned empty, causing 0 tools and
  403 on tool calls. allow_all_keys bypasses per-key restrictions.
- Add asyncio.sleep(0.5) between client connections to allow MCP SDK
  TaskGroup cleanup and avoid ExceptionGroup on connection close (MCP #915).

Test 2 (create_mcp_server 'auth value is provided'):
- Use userEvent.setup({ delay: null }) for instant keystrokes to avoid
  timeout from default typing delay on CI.
- Increase per-test timeout to 15000ms for CI environments.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: stabilize proxy unit tests for parallel execution

- test_response_polling_handler: add xdist_group to prevent heavy import OOM
- test_db_schema_migration: use temp dir for worker isolation, sync schema.prisma index
- test_custom_tokenizer_bug: use lighter tokenizer to prevent OOM in parallel

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: add auth overrides to more spend tracking and model info tests

- Fix test_ui_view_spend_logs_pagination missing auth override (401)
- Fix test_view_spend_tags missing auth override (401)
- Fix test_view_spend_tags_no_database missing auth override (401)
- Fix test_empty_model_list.py to use app.dependency_overrides instead of patch()
  for FastAPI dependency injection auth

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): use patch.object for aiohttp transport test to work in parallel execution

The @patch decorator was not intercepting the static method call in parallel
xdist workers. Using patch.object on the directly-imported class is more reliable.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(security): update minimatch from 10.2.1 to 10.2.4 in Dockerfile

The Docker image was explicitly pinning minimatch@10.2.1 which has HIGH
severity ReDoS vulnerabilities (GHSA-7r86-cg39-jmmj, GHSA-23c5-xmqv-rm74).
Update to 10.2.4 which includes fixes for both CVEs.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(ui): prevent MCP and TeamInfo test timeouts on CI

- Add userEvent.setup({ delay: null }) to all tests using userEvent in both files
- Add timeout: 15000 to tests with significant user interaction (typing, multiple clicks)
- Fixes: create_mcp_server Bearer Token test, TeamInfo cancel button test

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: stabilize parallel test execution and aiohttp transport test

- test_aiohttp_handler: rewrite transport test to not rely on static method mock
  (consistently fails in parallel xdist workers)
- test_proxy_cli: add xdist_group to prevent timeout during heavy imports
- test_swagger_chat_completions: add xdist_group to prevent timeout

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(security): add serialize-javascript override to fix GHSA-5c6j-r48x-rmvq

Add npm override for serialize-javascript>=7.0.3 in docs/my-website
to fix HIGH severity RCE vulnerability via RegExp.flags.
Also bump minimatch override to >=10.2.4.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* Fix flaky tests: remove broken Vertex model, add retries for Anthropic

- Remove vertex_ai/meta/llama-4-scout-17b-16e-instruct-maas from
  test_partner_models_httpx_streaming - consistently returns 400 BadRequest
- Add @pytest.mark.flaky(retries=6, delay=10) to test_function_call_parsing
  for transient Anthropic API overload errors
- Add @pytest.mark.flaky(retries=6, delay=10) to test_openai_stream_options_call
  for transient Anthropic InternalServerError

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(ci): add xdist_group(proxy_heavy) to prevent OOM in parallel proxy tests

- Add pytestmark = pytest.mark.xdist_group('proxy_heavy') to test_proxy_utils.py
- Change test_db_schema_migration.py from schema_migration to proxy_heavy group
- Add @pytest.mark.xdist_group('proxy_heavy') to test_proxy_server.py::test_health

Groups heavy proxy tests to run on same worker, avoiding worker OOM crashes.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* Fix vertex AI qwen global endpoint test to mock vertexai module import

The test_vertex_ai_qwen_global_endpoint_url test was failing because the
VertexAIPartnerModels.completion() method tries to 'import vertexai' before
any of the mocked code runs. In environments without google-cloud-aiplatform
installed, this import fails with a VertexAIError(status_code=400).

Fix by:
- Adding patch.dict('sys.modules', {'vertexai': MagicMock()}) to mock the
  vertexai module import
- Adding vertex_ai_location parameter to the acompletion call for completeness

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(ci): add xdist_group to health endpoint and watsonx tests for parallel stability

- test_health_liveliness_endpoint: add xdist_group('proxy_health') to prevent timeout
- test_watsonx_gpt_oss tests: add xdist_group('watsonx_heavy') to prevent mock interference

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): pre-populate WatsonX IAM token cache to prevent parallel test interference

The watsonx prompt transformation test was failing in parallel execution because
litellm.module_level_client.post mock was being interfered with by other tests.
Pre-populating the IAM token cache avoids the HTTP call entirely.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): add spend data polling with retries for e2e pass-through tests

- test_vertex_with_spend.test.js: Replace 15s fixed wait with polling loop
  (up to 6 attempts, 10s apart) for spend data to appear in DB
- Increase test timeout from 25s to 90s to accommodate polling
- base_anthropic_messages_tool_search_test.py: Add flaky(retries=3) for
  streaming test that depends on live Anthropic API

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(ci): reduce parallel workers from 8 to 4 for proxy tests to prevent OOM

- litellm_proxy_unit_testing_part2: -n 8 -> -n 4
- litellm_mapped_tests_proxy_part2: -n 8 -> -n 4, timeout 60 -> 120
- Worker crashes consistently caused by too many parallel proxy tests
  each loading the full FastAPI app and heavy dependency tree

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(db): add migration for SpendLogs composite index (startTime, request_id)

The @@index([startTime, request_id]) was added to schema.prisma but had no
corresponding migration. This caused test_aaaasschema_migration_check to fail
because prisma migrate diff detected the missing index.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(db): add migration for MCP available_on_public_internet default change to true

The schema.prisma changed the default for available_on_public_internet from
false to true, but no migration was created. This caused the schema migration
test to detect drift.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): increase server wait time and add retry to flaky external API tests

- test_basic_python_version.py: increase server startup wait from 60s to 90s
  for slower CI environments (fixes installing_litellm_on_python_3_13)
- test_a2a_agent.py: add flaky(retries=3, delay=5) for non-streaming test
  that depends on live A2A agent endpoint

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): add flaky retries to all intermittent external API tests for 0-fail CI

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(test): add auth overrides to file endpoint tests that return 500

The test_target_storage tests were getting 500 because the FastAPI auth
dependency wasn't overridden. Added app.dependency_overrides for proper
auth bypass in test environment.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

---------

Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>
2026-02-28 09:46:35 -08:00
yuneng-jiang
926d95cd19 [Feature] UI - Projects: Add delete project action to projects table
Add the ability to delete projects from the projects list page:
- New useDeleteProject hook calling DELETE /project/delete
- Actions column with TableIconActionButton (Delete variant)
- DeleteResourceModal with confirmation requiring project name input
- Alert warns that keys must be unlinked before deletion

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-28 09:40:15 -08:00
yuneng-jiang
b914c98562 [Feature] UI - Projects: Add project key table, project dropdown on key create/edit
Add project_id support across the key management UI:
- Project details page now shows a paginated key table with search
- Key create form includes a project dropdown that locks team selection
- Key edit/info views display project as read-only
- Beta alert banner on Projects page

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-28 00:04:06 -08:00
yuneng-jiang
a4b7a93a37
Merge pull request #22360 from BerriAI/litellm_ui_project_info
[Feature] UI - Projects: Add Project Details Page
2026-02-27 22:11:13 -08:00
yuneng-jiang
50dc7b520c
Update ui/litellm-dashboard/src/components/Projects/ProjectModals/CreateProjectModal.tsx
Co-authored-by: greptile-apps[bot] <165735046+greptile-apps[bot]@users.noreply.github.com>
2026-02-27 22:11:04 -08:00
yuneng-jiang
061703abc0 [Feature] UI - Projects: Add Project Details page with Edit modal
- Add ProjectDetailsPage with header, details card, spend/budget progress,
  model spend bar chart, keys placeholder, and team info card
- Refactor CreateProjectModal into base form pattern (ProjectBaseForm)
  shared between Create and Edit flows
- Add EditProjectModal with pre-filled form data from backend
- Add useProjectDetails and useUpdateProject hooks
- Add duplicate key validation for model limits and metadata
- Wire project ID click in table to navigate to detail view
- Move pagination inline with search bar

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-27 21:35:21 -08:00
yuneng-jiang
85590e4538
Merge pull request #22354 from BerriAI/litellm_cost_tracking_vitest
[Test] UI - CostTrackingSettings: Add comprehensive Vitest coverage
2026-02-27 21:24:02 -08:00
yuneng-jiang
c4a0174e00 test: add comprehensive Vitest coverage for CostTrackingSettings
Add 88 tests across 9 test files for the CostTrackingSettings component directory:
- provider_display_helpers.test.ts: 9 tests for helper functions
- how_it_works.test.tsx: 9 tests for discount calculator component
- add_provider_form.test.tsx: 7 tests for provider form validation
- add_margin_form.test.tsx: 9 tests for margin form with type toggle
- provider_discount_table.test.tsx: 12 tests for table editing and interactions
- provider_margin_table.test.tsx: 13 tests for margin table with sorting
- use_discount_config.test.ts: 11 tests for discount hook logic
- use_margin_config.test.ts: 12 tests for margin hook logic
- cost_tracking_settings.test.tsx: 15 tests for main component and role-based rendering

All tests passing. Coverage includes form validation, user interactions, API calls, state management, and conditional rendering.

Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
2026-02-27 21:16:41 -08:00
Ishaan Jaff
eea083fa4b
fix(mcp): default available_on_public_internet to true (#22331)
* fix(mcp): default available_on_public_internet to true

MCPs were defaulting to private (available_on_public_internet=false) which
was a breaking change. This reverts the default to public (true) across:
- Pydantic models (AddMCPServerRequest, UpdateMCPServerRequest, LiteLLM_MCPServerTable)
- Prisma schema @default
- mcp_server_manager.py YAML config + DB loading fallbacks
- UI form initialValue and setFieldValue defaults

* fix(ui): add forceRender to Collapse.Panel so toggle defaults render correctly

Ant Design's Collapse.Panel lazy-renders children by default. Without
forceRender, the Form.Item for 'Available on Public Internet' isn't
mounted when the useEffect fires form.setFieldValue, causing the Switch
to visually show OFF even though the intended default is true.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix(mcp): update remaining schema copies and MCPServer type default to true

Missed in previous commit per Greptile review:
- schema.prisma (root)
- litellm-proxy-extras/litellm_proxy_extras/schema.prisma
- litellm/types/mcp_server/mcp_server_manager.py MCPServer class

* ui(mcp): reframe network access as 'Internal network only' restriction

Replace scary 'Available on Public Internet' toggle with 'Internal network only'
opt-in restriction. Toggle OFF (default) = all networks allowed. Toggle ON =
restricted to internal network only. Auth is always required either way.

- MCPPermissionManagement: new label/tooltip/description, invert display via
  getValueProps/getValueFromEvent so underlying available_on_public_internet
  value is unchanged
- mcp_server_view: 'Public' → 'All networks', 'Internal' → 'Internal only' (orange)
- mcp_server_columns: same badge updates

---------

Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>
2026-02-27 20:06:07 -08:00
Ishaan Jaff
8ce358e303
[Feat] Agent RBAC Permission Fix - Ensure Internal Users cannot create agents (#22329)
* fix: enforce RBAC on agent endpoints — block non-admin create/update/delete

- Add /v1/agents/{agent_id} to agent_routes so internal users can
  access GET-by-ID (previously returned 403 due to missing route pattern)
- Add _check_agent_management_permission() guard to POST, PUT, PATCH,
  DELETE agent endpoints — only PROXY_ADMIN may mutate agents
- Add user_api_key_dict param to delete_agent so the role check works
- Add comprehensive unit tests for RBAC enforcement across all roles

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: mock prisma_client in internal user get-agent-by-id test

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* feat(ui): hide agent create/delete controls for non-admin users

Match MCP servers pattern: wrap '+ Add New Agent' button in
isAdmin conditional so internal users see a read-only agents view.
Delete buttons in card and table were already gated.
Update empty-state copy for non-admin users.
Add 7 Vitest tests covering role-based visibility.

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

---------

Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>
2026-02-27 18:32:39 -08:00
Chesars
ab8ffb0573 Merge upstream/main into fix-model-management-ui 2026-02-27 19:01:58 -03:00
Alejandro Tapia
18bc0d4ec9 reusable-credentials 2026-02-27 13:37:23 -08:00
yuneng-jiang
2613277ede [Feature] UI - Projects: Add Projects page with list and create flows
Add a new Projects page under ACCESS CONTROL in the left nav, positioned
between Teams and Internal Users. Projects sit between teams and keys in
the hierarchy for use-case management.

- ProjectsPage with Ant Design table (list, search, pagination)
- CreateProjectModal with team-scoped model selection
- React-query hooks for /project/list and /project/new
- New badge on Projects, removed from Access Groups
- Page metadata entry for test compliance

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-27 13:31:17 -08:00
Sameer Kankute
d9af321610 Fix free models working from UI 2026-02-27 10:08:44 +05:30
Dibyo Mukherjee
518cd3ef60 feat(ui): add key creation deep-links with SSO return URL support
Enables deep-linking directly to the key creation modal with prefilled
form data via URL parameters, including support for preserving these
deep-links through SSO authentication flows.

Key Creation Deep-links:
- Auto-open key creation modal via ?create=true parameter
- Prefill form fields from URL parameters (team_id, key_alias, models, etc.)
- Role-based access control for auto-open (requires write access)
- Race condition protection for redirect handling

Example: /ui?create=true&team_id=abc&key_alias=my-key&models=gpt-4,claude-3

SSO Return URL Preservation:
- Cookie-based return URL storage (works across ports for SSO flows)
- URL validation to prevent open redirect attacks
- Support for both dev and production environments

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-02-26 15:41:54 -05:00
yuneng-jiang
c3c79b9d80 [Fix] Virtual Keys pagination displays stale totals when filtering
When applying a key_alias filter on the Virtual Keys page, the pagination display (total count, page count) showed stale unfiltered values. The bug was that the table component tracked total_count only from the unfiltered useKeys hook, not from the filtered API response returned by useFilterLogic.

Fixes: When selecting a key alias that matches 1 key, the UI previously showed "Showing 1-50 of 509 results" and "Page 1 of 11" instead of the correct "Showing 1-1 of 1 results" and "Page 1 of 1".

Changes:
- Added filteredTotalCount state to useFilterLogic to track the total_count from filtered API responses
- Updated VirtualKeysTable to use filteredTotalCount (when set) instead of always using the unfiltered total
- Added comprehensive tests to prevent regression of pagination display logic

Type: 🐛 Bug Fix,  Test

Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
2026-02-26 12:28:43 -08:00
yuneng-jiang
947586b62d Merge remote-tracking branch 'origin' into litellm_paginated_key_alias 2026-02-26 10:28:35 -08:00
Ishaan Jaff
965ca117bc
feat(realtime guardrails): end_session_after_n_fails + Endpoint Settings wizard step (#22165)
* feat(realtime guardrails): end_session_after_n_fails + Endpoint Settings wizard step

Adds per-session violation thresholds and an optional endpoint-settings step
to the guardrail wizard for /v1/realtime.

Backend:
- Add end_session_after_n_fails, on_violation, realtime_violation_message fields
  to BaseLitellmParams (no DB migration — stored in existing JSON column)
- Store same fields on CustomGuardrail instance attrs
- Pass through in litellm_content_filter initializer
- Track _violation_count per RealTimeStreaming session; close backend_ws when
  on_violation=end_session OR violation count >= end_session_after_n_fails
- Use realtime_violation_message as the spoken text (falls back to guardrail
  error string if not configured)

UI (add_guardrail_form.tsx):
- Rename "Default Categories" step to "Topics"
- Add step 5 "Endpoint Settings (Optional)" for content filter guardrails
- Call type dropdown shows /v1/realtime
- Settings are in a collapsed accordion (closed by default)
- "End session after X violations" + on_violation radio + spoken message field

Tests: 2 new tests in test_realtime_streaming.py
- test_end_session_after_n_fails_closes_connection
- test_on_violation_end_session_closes_on_first_fail

* fix(test): move inline imports to module level in realtime streaming tests

* Update ui/litellm-dashboard/src/components/guardrails/add_guardrail_form.tsx

Co-authored-by: greptile-apps[bot] <165735046+greptile-apps[bot]@users.noreply.github.com>

---------

Co-authored-by: greptile-apps[bot] <165735046+greptile-apps[bot]@users.noreply.github.com>
2026-02-25 23:49:03 -08:00
Ishaan Jaff
3545584a00
Development environment setup (#22160)
* feat: add pretty view for realtime API logs in dashboard

- Create RealtimePrettyView component that renders structured session
  config, conversation turns with transcripts, and token breakdowns
- Update PrettyMessagesView to detect realtime responses (via
  isRealtimeResponse helper) and delegate to the new component
- Session card shows model, voice, modalities, temperature, instructions
  in a collapsible panel
- Conversation turns show status, per-turn token usage, and audio/text
  transcripts with appropriate icons
- Add 24 tests for RealtimePrettyView and 3 tests for PrettyMessagesView
- All 75 LogDetailsDrawer tests pass

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* chore: remove dev_config.yaml from tracked files

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* feat: show turn count in realtime pretty view session header and output header

- Add purple 'N turns' tag to Session card header for at-a-glance turn count
- Add 'Turns: N' to the Output section header next to tokens/cost
- Extend SectionHeader to accept optional turnCount prop
- Add 3 new tests for turn count display (singular, plural, output header)

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

* fix: address Greptile review feedback

- Remove response.audio.done and conversation.item.created from
  isRealtimeResponse() detection since the view doesn't render them;
  prevents misleading fallback for responses with only those events
- Remove dead code: index >= 0 is always true in .map() callback

Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>

---------

Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>
2026-02-25 23:20:03 -08:00
yuneng-jiang
ac3cfff93f Merge remote-tracking branch 'origin' into litellm_paginated_key_alias 2026-02-25 22:32:36 -08:00
yuneng-jiang
5a123f0e75 fixing ui build 2026-02-25 22:29:34 -08:00
yuneng-jiang
701ec62da6 [Feature] UI - Paginated Key Alias Select
Replace the non-paginated Key Alias filter with a new PaginatedKeyAliasSelect component that mirrors the existing PaginatedModelSelect pattern. This aligns the UI with the paginated /key/aliases endpoint from PR #22137.

Changes:
- Added useInfiniteKeyAliases hook for paginated key alias fetching
- Created PaginatedKeyAliasSelect component with infinite scroll (80% threshold)
- Updated keyAliasesCall in networking to accept page/size/search params
- Replaced Key Alias filter in Request Logs and Virtual Keys tables to use customComponent
- Removed fetchAllKeyAliases helper and related upfront fetching logic
- Added 22 tests for new component and hook; all existing tests pass (54 tests)

Fixes the issue where the UI was fetching all key aliases at once, causing performance issues with large key sets.

Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
2026-02-25 22:21:32 -08:00
Krish Dholakia
a9cb2674c0
feat(add-new-block_code_execution-guardrail): prevent agent from executing code (#22154)
Adds a new block_code_execution guardrail that detects markdown fenced code blocks
in request/response content and blocks or masks them by language. Includes full
UI integration, type definitions, compliance test dataset, and 26 unit tests.

Key guardrail capabilities:
- Regex-based fenced code block detection with configurable blocked languages
- Confidence scoring with tunable threshold
- Execution-intent heuristics (request-side only) with conflict resolution
- Block or mask actions for detected code
- Support for pre_call, post_call, and during_call event hooks

Security hardening:
- Response-side blocking skips intent heuristics (LLM output doesn't contain
  user intent phrases, so checking would silently disable post_call blocking)
- No-execution short-circuit includes conflict resolution: if both no-execution
  and execution phrases match, execution intent wins
- Tightened overly broad phrases to prevent trivial bypass
- _normalize_escaped_newlines only applies to pure-escaped payloads to avoid
  corrupting content that discusses escape sequences

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 22:02:14 -08:00
Ishaan Jaff
82cd14ea1d
feat(realtime): guardrails support for /v1/realtime WebSocket endpoint (#22152)
* feat(realtime): add guardrails query param to /v1/realtime WebSocket endpoint

- Add 'guardrails' query param (comma-separated) to realtime_websocket_endpoint
- Import websockets and websockets.exceptions at module level (fixes NameError in except clause)
- Split try/except into Phase 1 (pre-call) and Phase 2 (routing) so guardrail
  errors send back a typed error event before closing, while upstream errors
  close silently with 1011

* feat(ui): pass selectedGuardrails from sidebar to RealtimePlayground WebSocket URL

* docs(realtime): add guardrails section with dynamic passing examples
2026-02-25 21:34:22 -08:00
Krish Dholakia
c2c8870d2d
Add claims agent guardrails (5 categories + policy template) (#22113)
* Add claims agent guardrails with 243-case eval dataset

5 new category guardrails for healthcare claims agent chatbots:
- claims_fraud_coaching: fraud coaching, exaggeration, document forgery
- claims_phi_disclosure: unauthorized PHI access, bulk data extraction
- claims_prior_auth_gaming: code manipulation, medical necessity misrepresentation
- claims_system_override: system injection, rule bypass, role impersonation
- claims_medical_advice: medical advice (claims-context-aware)

Plus claims_agent_safety.yaml policy template combining all 5.

All 5 eval suites pass at 100% precision/recall/F1 (243 test cases).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* Add claims agent chatbot safety policy template

Combines the 5 claims guardrails into a single deployable policy template:
fraud coaching, PHI disclosure, prior-auth gaming, system override, and medical advice.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* Add guardrail benchmark results and UI compliance prompts

Adds benchmark results for claims, discrimination, and content filter guardrails.
Updates UI compliance prompt data.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* Remove duplicate "file an appeal" exception in claims_prior_auth_gaming.yaml

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* Remove unused claims_agent_safety.yaml policy template

The claims-agent-safety template in policy_templates.json references
individual category files in categories/, not this combined file.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 18:09:38 -08:00
yuneng-jiang
88bf8de3cf
Merge pull request #22119 from BerriAI/litellm_ui_mcp_auth_non_req
[Fix] UI - MCP Servers: Make auth value optional for create flow
2026-02-25 16:48:08 -08:00
yuneng-jiang
6ac3ed6b4e
Merge pull request #22122 from BerriAI/litellm_ui_spend_logs_duration
[Feature] UI - Logs: Use backend request_duration_ms and make Duration sortable
2026-02-25 16:47:22 -08:00
Krish Dholakia
4b9aba8fac
feat: add UI banner warning for detailed debug mode (#21527)
Add a prominent warning banner to the UI dashboard when detailed debug
mode (LITELLM_LOG=DEBUG) is enabled. This alerts users to significant
performance degradation caused by extensive diagnostic logging.

Backend changes:
- Enhanced /health/readiness endpoint to include log_level and
  is_detailed_debug fields
- Added detection using verbose_logger.getEffectiveLevel()
- Backward compatible - old clients ignore new fields

Frontend changes:
- Updated useHealthReadiness TypeScript interface
- Created DebugWarningBanner component using Ant Design Alert
- Integrated banner into dashboard layout below navbar
- Banner only shows when DEBUG level is active
- Non-dismissible to ensure users are aware of performance impact

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 16:32:59 -08:00
Ishaan Jaff
adba088df2
Realtime API: spend log storage, playground UI, tools logging, and guardrail support (#22105)
Backend - Spend Log Storage for Realtime Calls:
- Collect user voice transcripts and text input during WebSocket sessions
- Store collected messages in spend logs when store_prompts_in_spend_logs enabled
- Capture tool definitions from session.update and tool calls from response.done
- Enrich proxy_server_request with tools and response with tool_calls for UI

Backend - WebSocket Auth:
- Support browser-based auth via Sec-WebSocket-Protocol subprotocol
- Echo back subprotocol on WebSocket accept

UI - Realtime Playground:
- New RealtimePlayground component with WebSocket voice+text chat
- Mic recording (PCM16 24kHz), server VAD, audio playback, text input
- Handle binary WebSocket frames (Blob/ArrayBuffer decoding)
- Add /v1/realtime endpoint option to playground endpoint selector

UI - Tools Section for Realtime Logs:
- Extract tool calls from realtime response format (response.tool_calls
  and response.results[].response.output[].type=function_call)

Tests:
- 15 new backend tests for realtime streaming and spend log storage
- 4 new UI tests for realtime tool call extraction

Fixes pre-existing build errors:
- ToolPolicies.tsx: duplicate import, antd styles type
- create_key_button.tsx: missing message import

Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: Ishaan Jaff <ishaan-jaff@users.noreply.github.com>
2026-02-25 14:55:27 -08:00
yuneng-jiang
5140062c09 [Feature] UI - Logs: Use backend request_duration_ms and make Duration sortable
Use the backend-provided request_duration_ms field instead of computing
duration client-side from startTime/endTime. Add sort support for the
Duration column, which sends sortBy=request_duration_ms to the API.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-25 12:24:11 -08:00
yuneng-jiang
a4fd75fd31 [Fix] UI - MCP Servers: Make auth value optional for create flow
The backend validator and frontend form both enforced auth_value as
required when auth_type is api_key, bearer_token, or basic. Users who
want to provide auth dynamically (via per-request headers or OAuth2
flows) could not skip the field.

- Remove required validation from auth_value in create_mcp_server.tsx
  (keep whitespace-only rejection, matching the edit flow)
- Remove validate_credentials_requirements in NewMCPServerRequest
  (all downstream code already treats auth_value as optional)
- Add tests for the create MCP server component

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-02-25 12:04:00 -08:00
Krish Dholakia
12c4876891
Agents - assign tools (#22064)
* feat(proxy): add max_iterations limiter for agent session loops (#22058)

Adds a new proxy hook that enforces a per-session cap on the number of
LLM calls an agentic loop can make. Callers send a session_id with each
request, and the hook counts calls per session, returning 429 when the
configured max_iterations limit is exceeded.

- Uses Redis Lua script for atomic increment (multi-instance safe)
- Falls back to in-memory cache when Redis unavailable
- Follows parallel_request_limiter_v3 pattern
- Configurable via key metadata: {"max_iterations": 25}
- Session counters auto-expire via TTL (default 1hr)

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>

* feat: add new code execution dataset

* feat(agent_endpoints/): allow giving agents keys

* fix: ui fixes

* feat: allow assigning mcp servers to agents

* fix: eliminate duplicate DB queries in MCP agent auth and N+1 in agent listing (#22110)

- Extract _get_agent_object_permission helper so _get_allowed_mcp_servers_for_agent
  and _get_agent_tool_permissions_for_server share a single DB fetch instead of
  each independently querying the same agent row (was 1+N queries per MCP request)
- Use include={"object_permission": True} on find_many in get_all_agents_from_db
  to eagerly load permissions in one query instead of N+1
- Use include={"object_permission": True} on create/update/find_unique in all
  agent CRUD operations, removing attach_object_permission_to_dict follow-up calls

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 11:44:30 -08:00
yuneng-jiang
30e8151288 fixing build and tests 2026-02-25 11:30:09 -08:00
yuneng-jiang
b9d3fdf93e Merge remote-tracking branch 'origin' into ui_build_fix_feb25 2026-02-25 10:51:50 -08:00
yuneng-jiang
cd41b49061 fixing build 2026-02-25 10:51:42 -08:00
yuneng-jiang
243771f99a
Merge pull request #22108 from BerriAI/litellm_pricing_calc_tests
[Test] UI - Pricing Calculator: Add comprehensive unit tests
2026-02-25 10:51:12 -08:00
Krish Dholakia
5662228e20
feat(ui): add user filtering to usage page (#22059)
* feat(ui): add user filtering to usage page

Adds "User Usage" as a new view option in the usage page dropdown,
allowing admins to view and filter usage data by individual users
via the existing /user/daily/activity backend endpoint.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat(ui/): working usage filtering

* fix(ui): use single-select for user filter and add tests

The user entity type's backend endpoint only accepts a single user_id,
so the filter now uses single-select mode instead of multi-select.
Added tests for the new user entity type in EntityUsage and
UsageViewSelect. Updated CLAUDE.md and AGENTS.md with guidance on
UI/backend contract consistency and test coverage for new entity types.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* revert: remove unintended package-lock.json changes

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* revert: restore package-lock.json to merge base state

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 10:37:45 -08:00
yuneng-jiang
6ae7e84a0b [Test] UI - Pricing Calculator: Add comprehensive unit tests
Added unit tests for all pricing calculator components with 64 passing tests across 5 test files:
- multi_export_utils.test.ts (16 tests for PDF/CSV export functions)
- use_multi_cost_estimate.test.ts (15 tests for cost estimation hook)
- multi_export_dropdown.test.tsx (8 tests for export dropdown component)
- multi_cost_results.test.tsx (15 tests for results display and UI states)
- index.test.tsx (10 tests for main calculator component)

Also fixed missing page description for tool-policies page in page_metadata.ts.

Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
2026-02-25 10:25:25 -08:00
Shin
115b9a2d29 fix(ui): remove duplicate antd import in ToolPolicies
Duplicate import was causing UI build to fail:
- Line 4: import { Select, Switch, Tooltip } from 'antd'
- Line 5: import { Select, Tooltip } from 'antd' (duplicate)

Removed the duplicate line 5.
2026-02-25 18:09:17 +00:00
Krish Dholakia
00ab4d2067
feat: add new code execution dataset (#22065) 2026-02-24 20:58:23 -08:00
Ishaan Jaff
60bcb26dc8
feat(agents): assign virtual keys to agents (#22045)
* feat(agents): assign virtual keys to agents

- Add agent_id field to LiteLLM_VerificationToken (schema.prisma + _types.py)
- Pass agent_id through key generation endpoint so keys can be scoped to an agent
- Refactor Add Agent wizard to 3-step flow (Configure → Assign Key → Ready)
  - Configure: all agent fields, custom/other type with just name+description
  - Assign Key: create new key or reassign existing key to agent
  - URL is now optional for easy discovery
- Add "Agent" ownership option to Create Key modal on Virtual Keys page
  with agent selector dropdown
- Extract CreatedKeyDisplay into shared component, reused in both flows
- Add keyCreateForAgentCall networking helper
- Add test for agent_id key generation

* fix(agents): code quality fixes from self-review

- Fix test_generate_key_helper_fn_agent_id: remove bare except clause,
  use explicit assert mock_insert.called, use .kwargs for clean arg access
- Remove no-op conditional in handleNext (both branches were identical)
- Validate selectedExistingKey before calling keyUpdateCall
- Validate selectedAgentId before setting on formValues in create_key_button

* fix(ui): replace deprecated Tremor Button with Ant Design Button in CreatedKeyDisplay
2026-02-24 18:28:16 -08:00
Ishaan Jaff
4e84e4c607
fix(ui): show real tool names in logs for Anthropic format tools (#22048) 2026-02-24 18:16:04 -08:00
yuneng-jiang
3f1554c099
Merge pull request #21071 from atapia27/feat/healthcheck-model_id-fix
healthcheck-model_id-fix
2026-02-24 17:15:07 -08:00
Alejandro Tapia
80c09295ad Merge upstream/main - resolve health check conflicts 2026-02-24 17:09:05 -08:00
yuneng-jiang
9837a1bd2a
Merge pull request #22047 from BerriAI/litellm_key_info_page_email
[Feature] UI - Virtual Keys: Add KeyInfoHeader component
2026-02-24 17:04:17 -08:00