Coverage for agentos/tests/test_conversation.py: 0%
102 statements
« prev ^ index » next coverage.py v7.14.3, created at 2026-07-02 09:59 +0800
« prev ^ index » next coverage.py v7.14.3, created at 2026-07-02 09:59 +0800
1"""Tests for agentos.conversation.conversation."""
3from __future__ import annotations
5import pytest
6from agentos.conversation.conversation import (
7 ConversationManager,
8 ConversationConfig,
9 Message,
10 MessageRole,
11 TrimStrategy,
12)
15@pytest.fixture
16def conv():
17 return ConversationManager(ConversationConfig(max_messages=10, max_tokens=100000))
20def test_add_message(conv):
21 """添加单条消息。"""
22 msg = conv.add("user", "Hello")
23 assert msg.role == MessageRole.USER
24 assert msg.content == "Hello"
25 assert conv.message_count == 1
28def test_add_many(conv):
29 """批量添加消息。"""
30 msgs = conv.add_many([("user", "Hi"), ("assistant", "Hello there")])
31 assert len(msgs) == 2
32 assert conv.message_count == 2
35def test_get_context(conv):
36 """获取 OpenAI 兼容上下文。"""
37 conv.add("system", "You are helpful.")
38 conv.add("user", "Question?")
39 ctx = conv.get_context()
40 assert len(ctx) == 2
41 assert ctx[0]["role"] == "system"
42 assert ctx[1]["role"] == "user"
45def test_fifo_trim(conv):
46 """FIFO 裁剪:超出 max_messages 时移除最旧消息。"""
47 conv.config.max_messages = 5
48 conv.config.preserve_last_n = 2
49 for i in range(10):
50 conv.add("user", f"msg{i}")
51 assert conv.message_count <= 5
54def test_preserve_system(conv):
55 """裁剪时保留 system 消息。"""
56 conv.config.max_messages = 4
57 conv.config.preserve_last_n = 1
58 conv.config.preserve_system = True
59 conv.add("system", "System prompt")
60 for i in range(8):
61 conv.add("user", f"msg{i}")
62 system_msgs = [m for m in conv._messages if m.role == MessageRole.SYSTEM]
63 assert len(system_msgs) >= 1
64 assert system_msgs[0].content == "System prompt"
67def test_token_tracking(conv):
68 """token 统计。"""
69 conv.add("user", "A" * 300)
70 assert conv.token_count > 50
73def test_fork_and_switch(conv):
74 """对话分支:fork -> switch -> 验证。"""
75 conv.add("user", "msg1")
76 conv.add("assistant", "reply1")
77 snapshot = conv.fork("test-branch")
78 assert snapshot.label == "test-branch"
80 conv.add("user", "msg2")
81 assert conv.message_count == 3
83 conv.switch_branch(snapshot.snapshot_id)
84 assert conv.message_count == 2
87def test_fork_branch_not_found(conv):
88 """切换不存在分支抛出 KeyError。"""
89 with pytest.raises(KeyError):
90 conv.switch_branch("nonexistent")
93def test_merge_branch_append(conv):
94 """合并分支(追加模式)。"""
95 conv.add("user", "msg1")
96 snapshot = conv.fork("side")
97 conv.add("user", "msg2")
98 conv.add("user", "msg3")
99 conv.merge_branch(snapshot.snapshot_id, strategy="append")
100 assert conv.message_count >= 3
103def test_clear(conv):
104 """清空对话。"""
105 conv.add_many([("user", "a"), ("assistant", "b"), ("user", "c")])
106 conv.clear()
107 assert conv.message_count == 0
108 assert conv.token_count == 0
111def test_clear_keep_system(conv):
112 """清空但保留 system 消息。"""
113 conv.add("system", "sys")
114 conv.add("user", "q")
115 conv.add("assistant", "a")
116 conv.clear(keep_system=True)
117 assert conv.message_count == 1
118 assert conv._messages[0].content == "sys"
121def test_stats_tracking(conv):
122 """统计数据正确累加。"""
123 conv.add("user", "hello world")
124 conv.add("assistant", "hi there")
125 assert conv.stats.total_messages == 2
126 assert conv.stats.total_tokens > 0
127 assert conv.stats.oldest_timestamp > 0
130def test_message_id_unique(conv):
131 """每条消息 ID 唯一。"""
132 msgs = conv.add_many([("user", f"msg{i}") for i in range(5)])
133 ids = {m.message_id for m in msgs}
134 assert len(ids) == 5
137def test_empty_context(conv):
138 """空对话上下文。"""
139 ctx = conv.get_context()
140 assert ctx == []
143def test_get_system_prompt(conv):
144 """提取 system prompt。"""
145 conv.add("system", "Be concise.")
146 conv.add("user", "Q")
147 assert conv.get_system_prompt() == "Be concise."
150def test_importance_weighted_trim():
151 """重要性加权裁剪。"""
152 cfg = ConversationConfig(max_messages=5, trim_strategy=TrimStrategy.IMPORTANCE_WEIGHTED, preserve_last_n=2)
153 c = ConversationManager(cfg)
154 for i in range(10):
155 m = c.add("user", f"msg{i}")
156 m.importance = float(i % 3)
157 assert c.message_count <= 5
160def test_trim_stats_increment(conv):
161 """裁剪后 trim_count 递增。"""
162 conv.config.max_messages = 3
163 conv.config.preserve_last_n = 1
164 for i in range(8):
165 conv.add("user", f"msg{i}")
166 assert conv.stats.trim_count > 0