from translation.backends.deepl import DeepLTranslationBackend class _FakeResponse: def __init__(self, status_code, payload=None, text=""): self.status_code = status_code self._payload = payload or {} self.text = text def json(self): return self._payload class _FakeSession: def __init__(self, responses): self.responses = list(responses) self.calls = [] def post(self, url, *, headers, json, timeout): self.calls.append( { "url": url, "headers": headers, "json": json, "timeout": timeout, } ) response = self.responses.pop(0) if isinstance(response, Exception): raise response return response def test_deepl_translate_uses_persistent_session_and_connect_timeout(): backend = DeepLTranslationBackend( api_key="test-key", api_url="https://api.deepl.com/v2/translate", timeout=5.0, glossary_id="glossary-1", ) fake_session = _FakeSession( [ _FakeResponse( 200, payload={"translations": [{"text": "Product title"}]}, ) ] ) backend._session = fake_session result = backend.translate( "商品标题", target_lang="en", source_lang="zh", scene="ecommerce_search_query", ) assert result == "Product title" assert len(fake_session.calls) == 1 call = fake_session.calls[0] assert call["timeout"] == (2.0, 5.0) assert call["json"]["target_lang"] == "EN" assert call["json"]["source_lang"] == "ZH" assert call["json"]["glossary_id"] == "glossary-1" assert call["json"]["context"] def test_deepl_translate_retries_retryable_failures(monkeypatch): monkeypatch.setattr("translation.backends.deepl.time.sleep", lambda *_args, **_kwargs: None) backend = DeepLTranslationBackend( api_key="test-key", api_url="https://api.deepl.com/v2/translate", timeout=5.0, ) fake_session = _FakeSession( [ _FakeResponse(429, text="too many requests"), _FakeResponse(200, payload={"translations": [{"text": "dress"}]}), ] ) backend._session = fake_session result = backend.translate( "连衣裙", target_lang="en", source_lang="zh", scene="general", ) assert result == "dress" assert len(fake_session.calls) == 2