Co-authored-by: Carlo <carloantonio.patti@mistral.ai>
Co-authored-by: Mathias Gesbert <mathias.gesbert@mistral.ai>
Co-authored-by: Clement Sirieix <clem.sirieix@gmail.com>
Co-authored-by: Michel Thomazo <michel.thomazo@mistral.ai>
Co-authored-by: Clément Drouin <clement.drouin@mistral.ai>
Co-authored-by: Vincent Guilloux <vincent.guilloux@mistral.ai>
Co-authored-by: Thomas Kenbeek <thomas.kenbeek@mistral.ai>
Co-authored-by: Mistral Vibe <vibe@mistral.ai>
This commit is contained in:
Quentin 2026-02-27 17:31:58 +01:00 committed by GitHub
parent a560a47ce8
commit 5d2e01a6d7
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
139 changed files with 7152 additions and 1457 deletions

View file

@ -16,22 +16,13 @@ from vibe.core.types import (
@pytest.mark.asyncio
async def test_auto_compact_triggers_and_batches_observer(
telemetry_events: list[dict],
) -> None:
observed: list[tuple[Role, str | None]] = []
def observer(msg: LLMMessage) -> None:
observed.append((msg.role, msg.content))
async def test_auto_compact_emits_correct_events(telemetry_events: list[dict]) -> None:
backend = FakeBackend([
[mock_llm_chunk(content="<summary>")],
[mock_llm_chunk(content="<final>")],
])
cfg = build_test_vibe_config(auto_compact_threshold=1)
agent = build_test_agent_loop(
config=cfg, message_observer=observer, backend=backend
)
agent = build_test_agent_loop(config=cfg, backend=backend)
agent.stats.context_tokens = 2
events = [ev async for ev in agent.act("Hello")]
@ -50,14 +41,83 @@ async def test_auto_compact_triggers_and_batches_observer(
assert end.new_context_tokens >= 1
assert final.content == "<final>"
roles = [r for r, _ in observed]
assert roles == [Role.system, Role.user, Role.assistant]
assert observed[1][1] is not None and "<summary>" in observed[1][1]
assert observed[2][1] == "<final>"
auto_compact = [
e
for e in telemetry_events
if e.get("event_name") == "vibe/auto_compact_triggered"
if e.get("event_name") == "vibe.auto_compact_triggered"
]
assert len(auto_compact) == 1
@pytest.mark.asyncio
async def test_auto_compact_observer_sees_user_msg_not_summary() -> None:
"""Observer sees the original user message and final response.
Compact internals (summary request, LLM summary) are invisible
to the observer because they happen inside silent() / reset().
"""
observed: list[tuple[Role, str | None]] = []
def observer(msg: LLMMessage) -> None:
observed.append((msg.role, msg.content))
backend = FakeBackend([
[mock_llm_chunk(content="<summary>")],
[mock_llm_chunk(content="<final>")],
])
cfg = build_test_vibe_config(auto_compact_threshold=1)
agent = build_test_agent_loop(
config=cfg, message_observer=observer, backend=backend
)
agent.stats.context_tokens = 2
[_ async for _ in agent.act("Hello")]
roles = [r for r, _ in observed]
assert roles == [Role.system, Role.user, Role.assistant]
assert observed[1][1] == "Hello"
assert observed[2][1] == "<final>"
@pytest.mark.asyncio
async def test_auto_compact_observer_does_not_see_summary_request() -> None:
"""The compact summary request and LLM response must not leak to observer."""
observed: list[tuple[Role, str | None]] = []
def observer(msg: LLMMessage) -> None:
observed.append((msg.role, msg.content))
backend = FakeBackend([
[mock_llm_chunk(content="<summary>")],
[mock_llm_chunk(content="<final>")],
])
cfg = build_test_vibe_config(auto_compact_threshold=1)
agent = build_test_agent_loop(
config=cfg, message_observer=observer, backend=backend
)
agent.stats.context_tokens = 2
[_ async for _ in agent.act("Hello")]
contents = [c for _, c in observed]
assert "<summary>" not in contents
assert all("compact" not in (c or "").lower() for c in contents)
@pytest.mark.asyncio
async def test_compact_replaces_messages_with_summary() -> None:
"""After compact, messages list contains only system + summary."""
backend = FakeBackend([
[mock_llm_chunk(content="<summary>")],
[mock_llm_chunk(content="<final>")],
])
cfg = build_test_vibe_config(auto_compact_threshold=1)
agent = build_test_agent_loop(config=cfg, backend=backend)
agent.stats.context_tokens = 2
[_ async for _ in agent.act("Hello")]
# After compact + final response: system, summary, final
assert agent.messages[0].role == Role.system
assert agent.messages[-1].role == Role.assistant
assert agent.messages[-1].content == "<final>"