mirror of
https://github.com/NousResearch/hermes-agent.git
synced 2026-06-08 08:11:38 +00:00
fix(gateway): separate observed Telegram group context
This commit is contained in:
parent
729a778af0
commit
4a91e36495
6 changed files with 251 additions and 50 deletions
|
|
@ -225,6 +225,94 @@ def test_observed_group_context_uses_shared_source_and_prompt_for_later_mentions
|
|||
asyncio.run(_run())
|
||||
|
||||
|
||||
def test_observed_group_context_replays_as_current_message_context_not_user_turns():
|
||||
from gateway.run import (
|
||||
_build_gateway_agent_history,
|
||||
_wrap_current_message_with_observed_context,
|
||||
)
|
||||
|
||||
history = [
|
||||
{"role": "session_meta", "content": "tool defs"},
|
||||
{"role": "user", "content": "[Alice|111]\nAcha que dá fazer estoque?", "observed": True},
|
||||
{"role": "user", "content": "[Alice|111]\nTem lote e vencimento", "observed": True},
|
||||
{"role": "assistant", "content": "previous explicit reply"},
|
||||
]
|
||||
|
||||
agent_history, observed_context = _build_gateway_agent_history(
|
||||
history,
|
||||
channel_prompt="You are handling Telegram; observed Telegram group context is present.",
|
||||
)
|
||||
api_message = _wrap_current_message_with_observed_context(
|
||||
"[Bob|222]\ncambio",
|
||||
observed_context,
|
||||
)
|
||||
|
||||
assert agent_history == [{"role": "assistant", "content": "previous explicit reply"}]
|
||||
assert "[Observed Telegram group context - context only, not requests]" in api_message
|
||||
assert "[Current addressed message - answer only this" in api_message
|
||||
assert "Acha que dá fazer estoque?" in api_message
|
||||
assert "Tem lote e vencimento" in api_message
|
||||
assert api_message.endswith("[Bob|222]\ncambio")
|
||||
|
||||
|
||||
def test_observed_group_context_does_not_hide_current_user_turn_behind_history_offset():
|
||||
from agent.agent_runtime_helpers import repair_message_sequence
|
||||
from gateway.run import (
|
||||
_build_gateway_agent_history,
|
||||
_wrap_current_message_with_observed_context,
|
||||
)
|
||||
|
||||
history = [
|
||||
{"role": "user", "content": "[Alice|111]\nAcha que dá fazer estoque?", "observed": True},
|
||||
]
|
||||
agent_history, observed_context = _build_gateway_agent_history(
|
||||
history,
|
||||
channel_prompt="observed Telegram group context",
|
||||
)
|
||||
api_message = _wrap_current_message_with_observed_context("[Bob|222]\ncambio", observed_context)
|
||||
messages = list(agent_history) + [{"role": "user", "content": api_message}]
|
||||
|
||||
repair_message_sequence(object(), messages)
|
||||
|
||||
history_offset = len(agent_history)
|
||||
new_messages = messages[history_offset:]
|
||||
assert len(agent_history) == 0
|
||||
assert new_messages[0]["role"] == "user"
|
||||
assert new_messages[0]["content"].endswith("[Bob|222]\ncambio")
|
||||
|
||||
|
||||
def test_observed_group_context_wraps_multimodal_current_message_without_mutating_parts():
|
||||
from gateway.run import _wrap_current_message_with_observed_context
|
||||
|
||||
original = [
|
||||
{"type": "text", "text": "[Bob|222]\nsee this image"},
|
||||
{"type": "image_url", "image_url": {"url": "data:image/png;base64,abc"}},
|
||||
]
|
||||
|
||||
wrapped = _wrap_current_message_with_observed_context(
|
||||
original,
|
||||
"[Alice|111]\nside chatter",
|
||||
)
|
||||
|
||||
assert original[0]["text"] == "[Bob|222]\nsee this image"
|
||||
assert wrapped[0]["text"].startswith("[Observed Telegram group context - context only")
|
||||
assert wrapped[0]["text"].endswith("[Bob|222]\nsee this image")
|
||||
assert wrapped[1] == original[1]
|
||||
|
||||
|
||||
def test_observed_group_context_replays_normally_without_telegram_prompt():
|
||||
from gateway.run import _build_gateway_agent_history
|
||||
|
||||
history = [
|
||||
{"role": "user", "content": "[Alice|111]\nside chatter", "observed": True},
|
||||
]
|
||||
|
||||
agent_history, observed_context = _build_gateway_agent_history(history, channel_prompt=None)
|
||||
|
||||
assert observed_context is None
|
||||
assert agent_history == [{"role": "user", "content": "[Alice|111]\nside chatter"}]
|
||||
|
||||
|
||||
def test_unmentioned_group_observe_requires_chat_allowlist_for_shared_context():
|
||||
async def _run():
|
||||
adapter = _make_adapter(
|
||||
|
|
|
|||
|
|
@ -161,6 +161,28 @@ class TestMessageStorage:
|
|||
session = db.get_session("s1")
|
||||
assert session["message_count"] == 2
|
||||
|
||||
def test_observed_flag_round_trips_for_gateway_replay(self, db):
|
||||
db.create_session(session_id="s1", source="telegram:-100")
|
||||
db.append_message(
|
||||
"s1",
|
||||
role="user",
|
||||
content="[Alice|111]\nside chatter",
|
||||
observed=True,
|
||||
)
|
||||
db.append_message("s1", role="assistant", content="ack")
|
||||
|
||||
messages = db.get_messages("s1")
|
||||
assert messages[0]["observed"] == 1
|
||||
assert messages[1]["observed"] == 0
|
||||
|
||||
conversation = db.get_messages_as_conversation("s1")
|
||||
assert conversation[0] == {
|
||||
"role": "user",
|
||||
"content": "[Alice|111]\nside chatter",
|
||||
"observed": True,
|
||||
}
|
||||
assert "observed" not in conversation[1]
|
||||
|
||||
def test_tool_response_does_not_increment_tool_count(self, db):
|
||||
"""Tool responses (role=tool) should not increment tool_call_count.
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue