from fam_edge.model_adapters.ollama_adapter import OllamaAdapter def _cfg(**overrides): base = { "provider": "ollama", "role": "text", "model_name": "qwen2.5:7b", "base_url": "http://localhost:11434", "circuit_breaker": {"enabled": False}, } base.update(overrides) return base class _FakeResp: def __init__(self, status_code=200, text=""): self.status_code = status_code self.text = text def json(self): return {"response": "ok"} def test_warm_up_success(monkeypatch): calls = {} def fake_post(url, json=None, timeout=None): calls["url"] = url calls["json"] = json calls["timeout"] = timeout return _FakeResp(200) monkeypatch.setattr( "fam_edge.model_adapters.ollama_adapter.requests.post", fake_post) a = OllamaAdapter(_cfg()) assert a.warm_up() is True assert calls["url"] == "http://localhost:11434/api/generate" assert calls["json"]["model"] == "qwen2.5:7b" # 只为触发加载,不需要真的生成长文本 assert calls["json"]["options"]["num_predict"] == 1 def test_warm_up_http_error_returns_false(monkeypatch): monkeypatch.setattr( "fam_edge.model_adapters.ollama_adapter.requests.post", lambda url, json=None, timeout=None: _FakeResp(500, "boom")) a = OllamaAdapter(_cfg()) assert a.warm_up() is False def test_warm_up_exception_does_not_raise(monkeypatch): """核心诉求: 预热失败(比如 Ollama 服务当时没起来)不能抛异常影响主服务 启动,只应该记警告日志、返回 False。""" def raise_err(url, json=None, timeout=None): raise ConnectionError("refused") monkeypatch.setattr( "fam_edge.model_adapters.ollama_adapter.requests.post", raise_err) a = OllamaAdapter(_cfg()) assert a.warm_up() is False def test_warm_up_uses_generous_timeout_for_cold_start(monkeypatch): """核心诉求: 冷启动实测能到 1-2 分钟,预热请求的超时不能沿用问答的短超时。""" captured = {} def fake_post(url, json=None, timeout=None): captured["timeout"] = timeout return _FakeResp(200) monkeypatch.setattr( "fam_edge.model_adapters.ollama_adapter.requests.post", fake_post) a = OllamaAdapter(_cfg(timeout=20)) # chat() 用的短超时 a.warm_up() assert captured["timeout"] >= 120