fix(runtime): release 2.7.1 with consistent ADB and failure diagnostics
This commit is contained in:
1 parent
b2316ca249
commit
8bf59897bb
24 files changed
+792
-45
No files matched your search
@@ -0,0 +1,64 @@
|
||||
"""Hopper failures must not become successful negative lookups."""
|
||||
|
||||
import asyncio
|
||||
from importlib import import_module
|
||||
from types import SimpleNamespace
|
||||
from unittest.mock import AsyncMock, Mock
|
||||
|
||||
import pytest
|
||||
|
||||
from artemis.agents.hopper.hopper import HopperError, HopperOutput
|
||||
|
||||
module = import_module("artemis.agents.hopper.hopper")
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
@pytest.mark.parametrize("invalid", [None, {}, {"found": True, "output": " ", "reason": "Empty"}])
|
||||
async def test_invalid_extraction_switches_to_fallback(monkeypatch, invalid):
|
||||
good = HopperOutput(found=True, output="com.example.app", reason="Matched")
|
||||
primary = SimpleNamespace(ainvoke=AsyncMock(return_value=invalid))
|
||||
secondary = SimpleNamespace(ainvoke=AsyncMock(return_value=good))
|
||||
factory = Mock(
|
||||
side_effect=[
|
||||
SimpleNamespace(with_structured_output=lambda _: primary),
|
||||
SimpleNamespace(with_structured_output=lambda _: secondary),
|
||||
]
|
||||
)
|
||||
monkeypatch.setattr(module, "get_llm", factory)
|
||||
assert (
|
||||
await module.hopper(SimpleNamespace(data_engine=None), "Find app", "com.example.app")
|
||||
== good
|
||||
)
|
||||
assert primary.ainvoke.await_count == secondary.ainvoke.await_count == 1
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
@pytest.mark.parametrize("use_fallback", [False, True])
|
||||
async def test_exhausted_extraction_raises_a_distinct_error(monkeypatch, use_fallback):
|
||||
model = SimpleNamespace(ainvoke=AsyncMock(return_value=None))
|
||||
monkeypatch.setattr(
|
||||
module, "get_llm", lambda **_: SimpleNamespace(with_structured_output=lambda _: model)
|
||||
)
|
||||
with pytest.raises(HopperError, match="模型未能完成数据提取"):
|
||||
await module.hopper(
|
||||
SimpleNamespace(data_engine=None), "Find app", "packages", use_fallback=use_fallback
|
||||
)
|
||||
assert model.ainvoke.await_count == (2 if use_fallback else 1)
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
async def test_cancelled_extraction_never_uses_fallback(monkeypatch):
|
||||
model = SimpleNamespace(ainvoke=AsyncMock(side_effect=asyncio.CancelledError))
|
||||
monkeypatch.setattr(
|
||||
module, "get_llm", lambda **_: SimpleNamespace(with_structured_output=lambda _: model)
|
||||
)
|
||||
with pytest.raises(asyncio.CancelledError):
|
||||
await module.hopper(SimpleNamespace(data_engine=None), "Find app", "packages")
|
||||
assert model.ainvoke.await_count == 1
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
async def test_model_setup_failure_is_not_reported_as_missing_data(monkeypatch):
|
||||
monkeypatch.setattr(module, "get_llm", Mock(side_effect=ValueError("invalid model settings")))
|
||||
with pytest.raises(HopperError, match="模型未能完成数据提取"):
|
||||
await module.hopper(SimpleNamespace(data_engine=None), "Find app", "packages")
|
||||
Reference in new issue
Block a user