from unittest.mock import MagicMock, patch import pytest from src import ai_client from src.result_types import Result, ErrorInfo, ErrorKind def test_send_public_api_returns_result() -> None: with patch.object(ai_client, "set_provider"): with patch.object(ai_client, "_send_gemini", return_value=Result(data="hello")) as mock_send: r = ai_client.send("system", "user") assert isinstance(r, Result) assert r.ok assert r.data == "hello" def test_send_does_not_emit_deprecation() -> None: import warnings with warnings.catch_warnings(record=True) as w: warnings.simplefilter("always") with patch.object(ai_client, "set_provider"): with patch.object(ai_client, "_send_gemini", return_value=Result(data="hi")): r = ai_client.send("system", "user") assert r.ok and r.data == "hi" assert not any(issubclass(x.category, DeprecationWarning) for x in w) def test_send_preserves_errors() -> None: err = ErrorInfo(kind=ErrorKind.RATE_LIMIT, message="slow down", source="test") with patch.object(ai_client, "set_provider"): with patch.object(ai_client, "_send_gemini", return_value=Result(data="", errors=[err])): r = ai_client.send("system", "user") assert not r.ok assert r.errors == [err] def test_send_returns_empty_data_with_error_on_auth_failure() -> None: err = ErrorInfo(kind=ErrorKind.AUTH, message="bad key", source="test") with patch.object(ai_client, "set_provider"): with patch.object(ai_client, "_send_gemini", return_value=Result(data="", errors=[err])): r = ai_client.send("system", "user") assert not r.ok assert r.data == "" def test_classify_gemini_error_returns_error_info() -> None: from src.ai_client import _classify_gemini_error class FakeRateLimitError(Exception): pass e = FakeRateLimitError("rate limited") info = _classify_gemini_error(e, source="test.gemini") assert isinstance(info, ErrorInfo) assert info.kind == ErrorKind.RATE_LIMIT assert info.source == "test.gemini" assert info.original is e