* refactor: re-architect tests to mirror the codebase
* Update tests.yml
* fix: add missing tool_error imports after registry refactor
* fix(tests): replace patch.dict with monkeypatch to prevent env var leaks under xdist
patch.dict(os.environ) can leak TERMINAL_ENV across xdist workers,
causing test_code_execution tests to hit the Modal remote path.
* fix(tests): fix update_check and telegram xdist failures
- test_update_check: replace patch("hermes_cli.banner.os.getenv") with
monkeypatch.setenv("HERMES_HOME") — banner.py no longer imports os
directly, it uses get_hermes_home() from hermes_constants.
- test_telegram_conflict/approval_buttons: provide real exception classes
for telegram.error mock (NetworkError, TimedOut, BadRequest) so the
except clause in connect() doesn't fail with "catching classes that do
not inherit from BaseException" when xdist pollutes sys.modules.
* fix(tests): accept unavailable_models kwarg in _prompt_model_selection mock
When context compression fires during run_conversation() in the gateway,
the compressed messages were silently lost on the next turn. Two bugs:
1. Agent-side: _flush_messages_to_session_db() calculated
flush_from = max(len(conversation_history), _last_flushed_db_idx).
After compression, _last_flushed_db_idx was correctly reset to 0,
but conversation_history still had its original pre-compression
length (e.g. 200). Since compressed messages are shorter (~30),
messages[200:] was empty — nothing written to the new session's
SQLite.
Fix: Set conversation_history = None after each _compress_context()
call so start_idx = 0 and all compressed messages are flushed.
2. Gateway-side: history_offset was always len(agent_history) — the
original pre-compression length. After compression shortened the
message list, agent_messages[200:] was empty, causing the gateway
to fall back to writing only a user/assistant pair, losing the
compressed summary and tail context.
Fix: Detect session splits (agent.session_id != original) and set
history_offset = 0 so all compressed messages are written to JSONL.