Files
teknium1 b2e139b157 test: compaction property + liveness E2E on seeded random sessions (C4)
Class C4 (context compression correctness/liveness). A real AIAgent + SessionDB on disk drives
seeded random sessions (tool-pair heavy incl. parallel calls, huge single turns, image parts,
long answers, single tool results larger than the whole threshold, a cron-shaped single job
turn with 14 tool rounds, a provider whose real window is smaller than the configured one)
against the recording fake provider. After every turn and for every request it asserts:
bounded wall time and summarizer calls, all scripted steps consumed or an explicit error,
no user message lost from state.db (live or compacted=1), superseded rows always have a live/
archived copy, tool_call/tool_result pairs matched in live rows and in every request, system
prompt stable, the in-flight ask (cron job prompt) after every summary (#100818), and
persisted == sent: state.db at request time is exactly the request's history prefix, live rows
equal the in-memory history, and a fresh agent resumed from state.db continues identically.
Exposed the stale current_turn_user_idx bug fixed in the previous commit.
2026-09-23 14:54:36 -07:00

58 lines
2.1 KiB
Python

"""Lane-private fixtures for the compaction suites (one fake provider per module, one session per test)."""
from __future__ import annotations
import pytest
from tests.e2e.core.compaction._helpers import (
SLOW_SUMMARY_TIMEOUT_SECONDS,
THRESHOLD_TOKENS,
Scenario,
compaction_config,
start_provider,
write_home,
)
@pytest.fixture(scope="module")
def provider():
server, dispatch = start_provider()
try:
yield server, dispatch
finally:
server.stop()
@pytest.fixture
def make_scenario(provider, tmp_path, monkeypatch):
"""Build a Scenario with its own HERMES_HOME/state.db; closes every agent + DB at teardown."""
server, dispatch = provider
made: list[Scenario] = []
def make(mode: str = "good", *, extra: str = "", platform: str = "cli", window: int | None = None,
threshold_tokens: int = THRESHOLD_TOKENS, name: str = "hermes_home") -> Scenario:
# The hermetic root conftest already isolates HERMES_HOME per test; HOME stays put because the
# state.db live-system guard treats $HOME/.hermes as production.
hermes_home = tmp_path / name
monkeypatch.setenv("HERMES_HOME", str(hermes_home))
import hermes_state
monkeypatch.setattr(hermes_state, "DEFAULT_DB_PATH", hermes_home / "state.db")
slow = mode == "slow"
if slow:
# The compression request timeout has a 300 s production floor; pin it (and the host idle
# watchdog) to seconds so a hung summarizer is judged inside a unit-test budget.
import agent.auxiliary_client as aux
monkeypatch.setattr(aux, "_COMPRESSION_TIMEOUT_FLOOR_SECONDS", SLOW_SUMMARY_TIMEOUT_SECONDS)
extra += f" context_timeout_seconds: {SLOW_SUMMARY_TIMEOUT_SECONDS}\n"
write_home(hermes_home, server.base_url,
compaction_config(extra=extra, slow=slow, threshold_tokens=threshold_tokens))
sc = Scenario(server=server, dispatch=dispatch, home=hermes_home, mode=mode, platform=platform, window=window)
made.append(sc)
return sc
yield make
for sc in made:
sc.close()