Commit graph

11767 commits

Author SHA1 Message Date
yuneng-jiang
8fc31a7b3a
Merge branch 'litellm_yj_may1_2' into chore/router-override-trust 2026-05-01 17:26:04 -07:00
shivam
1f3d9a32f9
Fix policy registry teardown in tests
Reset the policy ID index during policy engine test cleanup so stale policy versions cannot leak between tests.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-05-01 17:25:38 -07:00
Ryan Crabbe
01ef723c3f
Merge remote-tracking branch 'origin/litellm_internal_staging' into litellm_fix-ag-not-resolved 2026-05-01 17:21:29 -07:00
yuneng-jiang
aa2cace304
Merge pull request #27026 from BerriAI/litellm_/flamboyant-mendeleev-481c14
[Fix] Proxy/Key Management: Honor team_member_permissions /key/list In /key/list Endpoint
2026-05-01 17:20:57 -07:00
Claude
0edbe6b3dc
test(router): cover _try_early_resolve_deployments_for_model_not_in_names
Some checks failed
Unit Tests: Caching (Redis) / caching-redis (push) Has been cancelled
Unit Tests: Proxy DB Operations / assert-shard-coverage (push) Has been cancelled
Unit Tests: Security / security (push) Has been cancelled
Unit Tests: Proxy DB Operations / budgets (push) Has been cancelled
Unit Tests: Proxy DB Operations / custom-logging (push) Has been cancelled
Unit Tests: Proxy DB Operations / auth-checks (push) Has been cancelled
Unit Tests: Proxy DB Operations / db-and-spend (push) Has been cancelled
Unit Tests: Proxy DB Operations / endpoints-and-responses (push) Has been cancelled
Unit Tests: Proxy DB Operations / guardrails-hooks (push) Has been cancelled
Unit Tests: Proxy DB Operations / jwt-and-keys (push) Has been cancelled
Unit Tests: Proxy DB Operations / key-generation (push) Has been cancelled
Unit Tests: Proxy DB Operations / logging-misc (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-runtime (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-server-core (push) Has been cancelled
Unit Tests: Proxy DB Operations / schema-migration (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-utils (push) Has been cancelled
The router_code_coverage CI check requires every function in router.py to
be referenced by at least one test under tests/{local_testing,
router_unit_tests,test_litellm} in a file with "router" in its name.
The recently-extracted helper had no direct test, so the check failed
with "0.45% of functions in router.py are not tested".

Add a focused test that exercises the four return paths: model already
in self.model_names, no fallback applies, pattern-router match, and
default_deployment substitution (also asserting the stored default
isn't mutated).

https://claude.ai/code/session_019AVp1XL7RT9RxRe4qRLkay
2026-05-02 00:18:45 +00:00
shivam
536a24c5ca
Fix runtime policy attachment initialization
Mark runtime-created policies and attachments initialized so global policy attachments created from the policy builder apply immediately without requiring a restart.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-05-01 17:11:57 -07:00
user
4ea32d13c9
fix(proxy): redact MCP server URL and headers for non-admin viewers (VERIA-8)
Many MCP integrations (Zapier, etc.) embed an upstream API key
directly in the server URL, e.g.
``https://actions.zapier.com/mcp/<api-key>/sse``. The list and
single-server endpoints were returning the full URL to any
authenticated user — `_redact_mcp_credentials` only stripped the
explicit ``credentials`` field, and `_sanitize_mcp_server_for_virtual_key`
only ran for restricted virtual keys. Non-admin internal users could
read the dashboard, click the unmask toggle, and exfiltrate the raw
token.

Add `_sanitize_mcp_server_for_non_admin` that runs on top of the
existing credential redaction and clears the credential-bearing
fields:

- ``url`` (the primary leak vector)
- ``spec_path`` (OpenAPI spec URLs that may carry tokens)
- ``static_headers`` / ``extra_headers`` (Authorization)
- ``env`` (arbitrary secrets)
- ``authorization_url`` / ``token_url`` / ``registration_url``

Identity fields (``server_id``, ``alias``, ``mcp_info``, etc.) are
preserved so the UI can still list servers a non-admin's team has
access to.

Apply the new sanitizer in `fetch_all_mcp_servers` and the per-server
fetch path right after the existing virtual-key branch. Update the
existing `test_list_mcp_servers_non_admin_user_filtered` assertions
that previously checked URL visibility.

Frontend defense-in-depth: hide the URL unmask toggle on
`mcp_server_view.tsx` unless the viewer is a proxy admin.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 23:59:38 +00:00
mateo-berri
9d945fe23b
Fix access-group bypass via litellm-model fallback path
When _get_all_deployments returns 0 candidates and the litellm-model
fallback branch (_get_deployment_by_litellm_model) finds deployments that
the access-group filter then empties, _access_group_filter_emptied_candidates
remained False (it was captured before that branch ran). The router would
then proceed to default fallbacks; the fallback model could have no
access_groups and short-circuit the filter, silently serving a caller
blocked by access-group restrictions.

Update the flag inside the litellm-model branch when filtering empties a
non-empty candidate set so the default-fallback guard still triggers.
2026-05-01 23:44:02 +00:00
yuneng-jiang
12c9a477f1
Merge pull request #27025 from BerriAI/litellm_fix-redis-key-generation-d88e
Fix Redis key generation to be stable across working directories
2026-05-01 16:41:12 -07:00
Yuneng Jiang
b8cf48a102
[Fix] Proxy/Key Management: Honor team_member_permissions /key/list In /key/list Endpoint
When a team grants /key/list via team_member_permissions, non-admin members
should see all keys for that team — same as a team admin. Previously the
classification in list_keys() only checked admin status, so permitted
members fell into the service-account-only path and could not see other
members' personal keys. Routes those members into the full-visibility set.
2026-05-01 16:37:22 -07:00
yuneng-jiang
8ed6c0cdea
Merge pull request #26846 from BerriAI/litellm_/pensive-bartik-e24048
[Fix] RBAC: Restore Admin Viewer Read Parity for Logs + Settings Pages
2026-05-01 16:36:36 -07:00
yuneng-jiang
57dd3891fb
Merge pull request #27024 from BerriAI/litellm_yj_may1
[Infra] Merge dev branch
2026-05-01 16:36:24 -07:00
Ryan Crabbe
bf4c250d86
fix: gate key access_group override on group's own assignment
Replaces the previous intersect-with-team.access_group_ids check, which
made the override unreachable in practice (the team-gate fallback already
covered every case the intersection allowed). The override now resolves
each of the key's access_group_ids via get_access_object and accepts the
group only if its assigned_team_ids includes the key's team_id, or its
assigned_key_ids includes the key's token. This fulfills the original ask
(a key can extend a team's allow-list via a group the admin granted to
that team or that specific key) while still rejecting foreign groups
referenced by team members of other teams.
2026-05-01 16:29:33 -07:00
Claude
6be7b77513
fix(tests): anchor VCR redis cassette key to repo root
`os.path.relpath` with no `start` arg uses the current working
directory, so running pytest from a subdirectory produced a
different Redis key than running from the repo root. CI-recorded
cassettes and locally-replayed runs would silently miss each
other's cache.

Anchor the path to the repo root (derived from `__file__`) so the
key is stable regardless of CWD.

https://claude.ai/code/session_018uCx7pcrkdUJZrCVMaTdPx
2026-05-01 23:27:18 +00:00
Yuneng Jiang
6499fa76de
[Fix] RBAC: Drop management_routes Write Fallback for Admin Viewer
Greptile P1: the unsafe-method branch of `_check_proxy_admin_viewer_access`
ended with a blanket `if route in management_routes: return`. That set is a
mix of reads (info/list — handled via the safe-method GET branch above) and
writes. The fallback let Admin Viewer POST to write endpoints not enumerated
in `_ADMIN_VIEWER_BLOCKED_WRITE_ROUTES`, including:
  - /team/block, /team/unblock, /team/permissions_update
  - /jwt/key/mapping/{new,update,delete}
  - /key/bulk_update
  - /key/{key_id}/reset_spend

Remove the fallback. The two remaining allow sets (admin_viewer_routes and
global_spend_tracking_routes) are both read-only, so removal does not affect
the legitimate POST-as-read cases (e.g. /spend/calculate, which is in
spend_tracking_routes ⊂ admin_viewer_routes).

Tests:
  - 8 new parametrized cases pinning each previously-leaking management write
    endpoint to 403 on POST for PROXY_ADMIN_VIEW_ONLY.
2026-05-01 16:15:21 -07:00
Mateo Wang
628ce9d5ef
Merge pull request #25856 from BerriAI/litellm_clean_litellm_oss_staging_04_01_2026
Litellm clean litellm oss staging 04 01 2026
2026-05-01 16:10:15 -07:00
yuneng-jiang
fba38d0e94
Merge pull request #26929 from BerriAI/litellm_fix_service_account_user_id_bypass
fix(proxy): reject user_id=None on non-admin analytics endpoints (cross-tenant disclosure)
2026-05-01 16:08:35 -07:00
mateo-berri
860f6b526e
Merge branch 'litellm_internal_staging' into litellm_access-group-routing-fix 2026-05-01 23:07:37 +00:00
Cursor Agent
60ca4424a6
Fix Vertex batch output edge cases
Some checks failed
Unit Tests: Caching (Redis) / caching-redis (push) Has been cancelled
Unit Tests: Proxy DB Operations / assert-shard-coverage (push) Has been cancelled
Unit Tests: Security / security (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-utils (push) Has been cancelled
Unit Tests: Proxy DB Operations / auth-checks (push) Has been cancelled
Unit Tests: Proxy DB Operations / budgets (push) Has been cancelled
Unit Tests: Proxy DB Operations / custom-logging (push) Has been cancelled
Unit Tests: Proxy DB Operations / db-and-spend (push) Has been cancelled
Unit Tests: Proxy DB Operations / endpoints-and-responses (push) Has been cancelled
Unit Tests: Proxy DB Operations / guardrails-hooks (push) Has been cancelled
Unit Tests: Proxy DB Operations / jwt-and-keys (push) Has been cancelled
Unit Tests: Proxy DB Operations / key-generation (push) Has been cancelled
Unit Tests: Proxy DB Operations / logging-misc (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-runtime (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-server-core (push) Has been cancelled
Unit Tests: Proxy DB Operations / schema-migration (push) Has been cancelled
2026-05-01 23:06:54 +00:00
Yuneng Jiang
c78144ccf0
Merge remote-tracking branch 'origin/litellm_internal_staging' into litellm_/pensive-bartik-e24048
# Conflicts:
#	ui/litellm-dashboard/src/app/(dashboard)/models-and-endpoints/ModelsAndEndpointsView.tsx
2026-05-01 16:04:09 -07:00
user
f53e8d6803 harden bedrock file bucket validation 2026-05-01 16:01:19 -07:00
Yuneng Jiang
a12b4249bd
[Fix] Proxy: Skip Personal Budget Hook When Reservation Covers Counter
The reservation path (PR #26845) atomically pre-fills `spend:user:{user_id}`
and admits at the strict-`<` boundary. The legacy `_PROXY_MaxBudgetLimiter`
pre-call hook re-reads the same counter with `>=`, so a reservation that
fills the counter to exactly `max_budget` (e.g. a request without a
`max_tokens` cap that falls back to reserving the smallest remaining
headroom) is rejected by the hook even though the reservation already
admitted it.

Skip the hook when the request's active `budget_reservation` covers
`spend:user:{user_id}`. The reservation is the source of truth for that
counter cross-pod; the legacy `>=` path remains in place for requests
without a reservation (e.g. paths that bypass the reservation entirely).

Reproduces as `tests/otel_tests/test_prometheus.py::test_user_budget_metrics`
on a fresh user with `max_budget=10` calling `fake-openai-endpoint` without
`max_tokens`. Adds focused unit coverage in
`tests/test_litellm/proxy/hooks/test_max_budget_limiter.py`.
2026-05-01 15:57:42 -07:00
mateo-berri
04e96a9bdc Merge remote-tracking branch 'origin/litellm_internal_staging' into litellm_clean_litellm_oss_staging_04_01_2026 2026-05-01 15:54:10 -07:00
Ryan Crabbe
f17d779666
fix: scope key access_group_ids override by team's assigned groups
A team member could set any access_group_ids on their key (e.g. a group
assigned only to a different team) and override the team's model
restriction. Intersect the key's access_group_ids with team_object.access_group_ids
in _key_access_group_grants_model so foreign groups are dropped before
model expansion. Adds a regression test that asserts expansion is never
called for foreign groups.
2026-05-01 15:54:03 -07:00
Mateo Wang
6458fe15fd
Merge pull request #26077 from BerriAI/litellm_vertex_cached_content_mutual_exclusion
fix(vertex_ai): omit system_instruction/tools/toolConfig when cachedContent set
2026-05-01 15:52:47 -07:00
ryan-crabbe-berri
4503dd18bb
Merge pull request #27012 from BerriAI/litellm_fix-post-call-guardrail
fix(guardrails): post-call guardrail must only fire once
2026-05-01 15:51:55 -07:00
Michael Riad Zaky
d3664947a4 fix metric labels for litellm-side rejects 2026-05-01 15:46:53 -07:00
Michael Riad Zaky
214dea43fa Remove unneeded metadata info from LangSmith
Some checks failed
Unit Tests: Caching (Redis) / caching-redis (push) Has been cancelled
Unit Tests: Proxy DB Operations / assert-shard-coverage (push) Has been cancelled
Unit Tests: Security / security (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-utils (push) Has been cancelled
Unit Tests: Proxy DB Operations / auth-checks (push) Has been cancelled
Unit Tests: Proxy DB Operations / budgets (push) Has been cancelled
Unit Tests: Proxy DB Operations / custom-logging (push) Has been cancelled
Unit Tests: Proxy DB Operations / db-and-spend (push) Has been cancelled
Unit Tests: Proxy DB Operations / endpoints-and-responses (push) Has been cancelled
Unit Tests: Proxy DB Operations / guardrails-hooks (push) Has been cancelled
Unit Tests: Proxy DB Operations / jwt-and-keys (push) Has been cancelled
Unit Tests: Proxy DB Operations / key-generation (push) Has been cancelled
Unit Tests: Proxy DB Operations / logging-misc (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-runtime (push) Has been cancelled
Unit Tests: Proxy DB Operations / proxy-server-core (push) Has been cancelled
Unit Tests: Proxy DB Operations / schema-migration (push) Has been cancelled
2026-05-01 15:42:12 -07:00
Mateo Wang
0b87bdff3d
Merge pull request #26976 from BerriAI/litellm_default_embedding_encoding_format
feat(embedding): default OpenAI-path encoding_format to float
2026-05-01 15:37:59 -07:00
user
ba1188117d fix cloud storage file guards 2026-05-01 15:34:11 -07:00
user
8ee599aa7d
fix(mcp): use canonical proxy_logging_obj, deny when MCP server is unresolvable
Greptile flagged two follow-ups on the OpenAPI/local-registry pre-call
check:

1. **P1 runtime crash via None proxy_logging_obj.**
   `kwargs.get("proxy_logging_obj")` is `None` on the MCP entry path,
   and `pre_call_tool_check` calls `proxy_logging_obj._create_mcp_request_object_from_kwargs`
   unconditionally after the security checks, which would have crashed
   every legitimate call with `AttributeError`. Source the logging
   object from `litellm.proxy.proxy_server` the same way
   `_handle_managed_mcp_tool` already does.

2. **P2 authorization-bypass window when mcp_server is None.**
   Previously the new check was guarded by `if mcp_server is not None`,
   so any local tool whose registry entry had no resolvable server (a
   startup-race window before `_initialize_tool_name_to_mcp_server_name_mapping`
   completes, or an orphaned registry entry) ran without the security
   check. Tools registered via openapi_to_mcp_generator are always tied
   to a server, so a missing one is a configuration/timing fault — fail
   the call with 503 instead of dispatching unguarded.

Tests: existing two pass with an added assertion that
`proxy_logging_obj` is non-None at the call site, plus a new test that
covers the 503 deny branch when the tool→server mapping is missing.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 22:28:46 +00:00
user
c84ae97899 Merge remote-tracking branch 'origin/litellm_internal_staging' into HEAD
# Conflicts:
#	litellm/litellm_core_utils/url_utils.py
#	litellm/llms/gemini/files/transformation.py
#	litellm/proxy/_lazy_openapi_snapshot.py
#	tests/test_litellm/litellm_core_utils/test_url_utils.py
#	tests/test_litellm/llms/gemini/files/test_gemini_files_transformation.py
#	tests/test_litellm/proxy/test_lazy_openapi_snapshot.py
2026-05-01 15:23:40 -07:00
Yuneng Jiang
8eca93470c
[Fix] Tests: Align Bedrock count-tokens endpoint assertions with URL-encoded model id
The endpoint builder in BedrockCountTokensConfig.get_bedrock_count_tokens_endpoint
percent-encodes the model id as a single path segment (d4dd865b1a, path-traversal
hardening). Update the four endpoint-URL assertions in TestBedrockCountTokensEndpoint
to expect `amazon.nova-lite-v1%3A0` instead of the literal `:0`, matching production
behavior already covered by test_count_tokens_endpoint_encodes_model_id.
2026-05-01 15:22:40 -07:00
user
7784b7f4ad chore(providers): allowlist URL model destinations 2026-05-01 15:18:31 -07:00
yuneng-jiang
d07cdd4481
Merge pull request #26838 from BerriAI/litellm_vcr-cassette-llm-tests-af37
tests(vcr): redis-backed vcrpy cache for offline LLM e2e replay
2026-05-01 15:16:52 -07:00
yuneng-jiang
8363fe00e1
Merge pull request #26841 from stuxf/fix/mcp-xff-trust-gate
chore(mcp): require trusted-proxy gate before honouring X-Forwarded-* on OAuth discovery
2026-05-01 15:08:40 -07:00
user
38fd1a99c4
fix(proxy): guard agent activity owned-fallback against null user_id
Greptile flagged that the new `created_by` fallback in
`/agent/daily/activity` resolves to `WHERE created_by IS NULL` when
`user_api_key_dict.user_id` is `None`, which would expose every
ownerless agent's rows to a service-account-style caller without a
user_id. Skip the fallback query entirely in that case so the caller
is treated as having no permitted agents (empty page, no DB hit).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 22:04:54 +00:00
user
5daf0168a8
fix(mcp): run pre_call_tool_check on OpenAPI/local-registry path (VERIA-7)
`execute_mcp_tool` dispatches in two ways: managed MCP servers go
through `_handle_managed_mcp_tool`, which calls
`MCPServerManager.pre_call_tool_check` to enforce allowed/banned tool
lists, key/team `object_permission` tool grants, and parameter
validation. OpenAPI-backed tools, however, were resolved via
`global_mcp_tool_registry` and dispatched directly to
`_handle_local_mcp_tool` — entirely skipping `pre_call_tool_check`.

A caller could invoke any registered OpenAPI tool regardless of their
key/team permissions, including administrative or destructive
operations on the upstream API.

Run `pre_call_tool_check` before the local-registry dispatch whenever
the resolved server is set (the same condition used to surface server
context to the managed path). Honor any guardrail-modified arguments
the hook returns. Errors raised by the hook propagate up before
`_handle_local_mcp_tool` runs.

Tests cover both directions: the pre-call hook fires when the local
tool resolves alongside a server, and a hook-raised HTTPException
prevents the local handler from being invoked.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 22:02:47 +00:00
user
3372db4f8f
fix(proxy): scope team and agent activity endpoints per-entity (VERIA-43)
Two related cross-tenant leaks in the daily-activity endpoints:

1. `/team/daily/activity` set a single `has_full_team_view` flag that
   went True if the caller was admin/perm-holder of ANY one of the
   requested teams. An admin of team A could pass `team_ids=A,B` and
   read team B's per-API-key breakdown even when they were only a
   plain member of team B. Require admin/permission on EVERY requested
   team for the unfiltered view; otherwise force fallback to the
   caller's own API keys for the whole request. Callers wanting wider
   coverage can split into separate requests.

2. `/agent/daily/activity` initialized an empty `where_condition` and
   returned every agent's spend/token rows on the proxy when
   `agent_ids` was omitted — the dashboard's "Top Agents Driving
   Spend" panel triggered this for any authenticated user. For
   non-admin callers, scope the query to agents they're permitted to
   invoke (`AgentRequestHandler.get_allowed_agents`) or, when their
   key/team has no explicit agent allowlist, to agents they created
   (`created_by`). Explicit `agent_ids` is intersected with the same
   permitted set rather than trusted. When the resolved set is empty,
   return an empty paginated page without issuing the query.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 21:54:32 +00:00
yuneng-jiang
3583ac1159
Merge pull request #26860 from stuxf/fix/provider-path-traversal
chore(security): encode upstream URL path identifiers
2026-05-01 14:47:52 -07:00
yuneng-jiang
dc681b9eb2
Merge pull request #26954 from BerriAI/claude/lucid-margulis-e99b6b
refactor(rate-limit): consolidate batch + dynamic limiter check/increment
2026-05-01 14:46:25 -07:00
yuneng-jiang
eca6feb6a6
Merge branch 'litellm_yj_may1' into codex/integration-host-credential-guard 2026-05-01 14:42:23 -07:00
user
6a5ecafdff
fix(prometheus): quote api_key for PromQL string literal in spend lookup
`get_daily_spend_from_prometheus` was interpolating the `api_key`
query parameter into a PromQL `hashed_api_key="..."` label matcher
with an f-string. Any caller of `/global/spend/logs` could inject a
bare `"` to terminate the matcher and append arbitrary PromQL
operators or extra metric selectors, exfiltrating cross-tenant
telemetry from the connected Prometheus instance.

Replace the f-string with `_quote_promql_string_literal`, which uses
`json.dumps` to render a complete Go-compatible double-quoted literal.
PromQL string literals follow Go's escape rules per
https://prometheus.io/docs/prometheus/latest/querying/basics/, and
JSON's quoting is a strict subset, so the same escape covers
backslash, embedded quote, and control-character cases without rolling
a bespoke escape table.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 21:38:19 +00:00
Mateo Wang
05439530c2
Merge branch 'litellm_internal_staging' into litellm_vcr-cassette-llm-tests-af37 2026-05-01 14:37:48 -07:00
mateo-berri
80415b472e tests(vcr): drop redundant comments and docstrings
Remove explanatory comments that restated what the code already says.
Kept only those that document non-obvious external contracts (the aiohttp
record-path patch's reason for re-feeding the body, and the warning
messages inside save_cassette that reach the user).
2026-05-01 14:36:48 -07:00
yuneng-jiang
ebd335da67
Merge pull request #27000 from BerriAI/litellm_fix_pdf_file_id_test
[Test] Anthropic: Use jsDelivr CDN For PDF Fixture URL
2026-05-01 14:36:25 -07:00
user
1b2756811e
fix(proxy): close project hijacking and key org IDOR
Two related authorization gaps in management endpoints:

1. `/project/update` evaluated permission against the team_id supplied in
   the request body. By passing `data.team_id` pointing at a team they
   admin, a caller could hijack any project — `_check_user_permission_for_project`
   was given the attacker's team_object and happily checked admin
   membership against that. Drop the team_object kwarg so the helper
   re-fetches the existing project's team. Also require admin rights on
   the destination team when reassigning a project across teams, so a
   team admin cannot shed projects into another team's namespace.

2. `/key/update` accepted any `organization_id` and only checked that
   the org existed before applying limits. A caller could thereby point
   their key at an arbitrary org. Add `_validate_caller_can_assign_key_org`
   which enforces the same membership rule already applied on the
   `/key/list` filter path (`validate_key_list_check`); proxy admins and
   no-change updates skip the check.

Tests cover both helpers in isolation: existing-team-admin allow,
unrelated-team admin deny, proxy-admin shortcut, org-member allow,
non-member deny, missing user_id deny, no-memberships deny.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 21:32:38 +00:00
yuneng-jiang
c2cea58567
Merge branch 'litellm_yj_may1' into codex/budget-race-enforcement 2026-05-01 14:32:18 -07:00
mateo-berri
53f71fbf4d tests(vcr): emit per-test verdicts via xdist controller's terminalreporter
Previous attempt wrote to sys.__stderr__ from the test fixture. Under
xdist, fixtures run inside worker subprocesses whose stderr is captured
by the controller and only released to the live log on test failure —
so passing tests' verdicts were silently swallowed.

Round-trip via report.user_properties: the worker-side fixture stashes
the verdict on user_properties, xdist serializes it onto the report,
and a controller-side pytest_runtest_logreport hook writes it via the
TerminalReporter (the same plugin that emits PASSED/FAILED markers).
TerminalReporter is resolved lazily on first hook call because it's
not yet registered when conftest's pytest_configure runs.

Verified locally in both serial and xdist modes.
2026-05-01 14:29:06 -07:00
Ryan Crabbe
a1fd150b98
style: black format test_deferred_guardrail_logging.py
Strip a trailing-whitespace line introduced by PR #26109. Black-only
change, no behavior impact — unblocks the lint check on this branch.
2026-05-01 14:28:20 -07:00