feat: add proxy support for httpx clients (#125)

Add proxy support for providers based on
[doc](https://www.python-httpx.org/advanced/proxies/):

- Add per-provider proxy support (HTTP and SOCKS5) for all 4 providers:
nvidia_nim, open_router, lmstudio, llamacpp
- Each provider gets its own env var (NVIDIA_NIM_PROXY,
OPENROUTER_PROXY, LMSTUDIO_PROXY, LLAMACPP_PROXY) for independent proxy
configuration

---------

Co-authored-by: Alishahryar1 <alishahryar2@gmail.com>
This commit is contained in:
arssing 2026-04-23 07:06:16 +07:00 committed by GitHub
parent e719e4aed2
commit 2fe15bd2cd
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
10 changed files with 107 additions and 9 deletions

View file

@ -202,6 +202,45 @@ async def test_get_provider_passes_http_timeouts_from_settings():
assert timeout.connect == 5.0
@pytest.mark.asyncio
async def test_get_provider_passes_proxy_from_settings():
"""Provider receives configured proxy and builds a proxied HTTP client."""
with (
patch("api.dependencies.get_settings") as mock_settings,
patch("providers.openai_compat.httpx.AsyncClient") as mock_http_client,
patch("providers.openai_compat.AsyncOpenAI") as mock_openai,
):
mock_settings.return_value = _make_mock_settings(
nvidia_nim_proxy="http://proxy.example:8080"
)
provider = get_provider()
assert isinstance(provider, NvidiaNimProvider)
mock_http_client.assert_called_once()
assert mock_http_client.call_args.kwargs["proxy"] == "http://proxy.example:8080"
assert (
mock_openai.call_args.kwargs["http_client"] is mock_http_client.return_value
)
@pytest.mark.asyncio
async def test_get_provider_ignores_non_string_proxy_value():
"""Mock settings without proxy attrs should not fail provider construction."""
with (
patch("api.dependencies.get_settings") as mock_settings,
patch("providers.openai_compat.AsyncOpenAI") as mock_openai,
):
mock_settings.return_value = _make_mock_settings(
nvidia_nim_proxy=MagicMock(name="proxy")
)
provider = get_provider()
assert isinstance(provider, NvidiaNimProvider)
assert mock_openai.call_args.kwargs["http_client"] is None
@pytest.mark.asyncio
async def test_get_provider_nvidia_nim_missing_api_key():
"""NVIDIA NIM with empty API key raises HTTPException 503."""