fix:修复记忆问题

This commit is contained in:
SengokuCola
2025-05-12 13:19:44 +08:00
parent 3a626a8d0c
commit 03589c6dcf
3 changed files with 48 additions and 147 deletions

View File

@@ -47,12 +47,9 @@ class HFCloopObservation:
if cycle.action_type == "reply":
consecutive_text_replies += 1
# 获取回复内容,如果不存在则返回'[空回复]'
response_text = cycle.response_info.get("response_text", [])
# 使用简单的 join 来格式化回复内容列表
formatted_response = "[空回复]" if not response_text else " ".join(response_text)
responses_for_prompt.append(formatted_response)
response_text = cycle.response_info.get("response_text", "[空回复]")
responses_for_prompt.append(response_text)
else:
# 一旦遇到非文本回复,连续性中断
break
# 根据连续文本回复的数量构建提示信息

View File

@@ -85,17 +85,17 @@ def init_prompt():
【回复原则】
1. 不回复(no_reply)适用:
- 话题无关/无聊/不感兴趣
- 最后一条消息是你自己发的且无人回应你
- 讨论你不懂的专业话题
- 你发送了太多消息,且无人回复
- 话题无关/无聊/不感兴趣
- 最后一条消息是你自己发的且无人回应你
- 讨论你不懂的专业话题
- 你发送了太多消息,且无人回复
2. 回复(reply)适用:
- 有实质性内容需要表达
- 有人提到你,但你还没有回应他
- 在合适的时候添加表情(不要总是添加)
- 如果你要回复特定某人的某句话或者你想回复较早的消息请在target中指定那句话的原始文本
- 有实质性内容需要表达
- 有人提到你,但你还没有回应他
- 在合适的时候添加表情(不要总是添加)
- 如果你要回复特定某人的某句话或者你想回复较早的消息请在target中指定那句话的原始文本
3. 回复target选择
-如果选择了target不用特别提到某个人的人名
- 除非有明确的回复目标否则不要添加target
@@ -106,9 +106,9 @@ def init_prompt():
-一次只回复一个话题
5. 自我对话处理:
- 如果是自己发的消息想继续,需自然衔接
- 避免重复或评价自己的发言
- 不要和自己聊天
- 如果是自己发的消息想继续,需自然衔接
- 避免重复或评价自己的发言
- 不要和自己聊天
决策任务
{action_options_text}
@@ -869,124 +869,6 @@ class PromptBuilder:
logger.error(traceback.format_exc())
return "[构建 Planner Prompt 时出错]"
async def build_planner_prompt_parallel(
self,
is_group_chat: bool,
chat_target_info: Optional[dict],
cycle_history: Deque["CycleDetail"],
observed_messages_str: str,
structured_info: str,
current_available_actions: Dict[str, str],
) -> str:
"""
构建并行规划器的提示词 (不依赖SubMind的思考结果)
这个方法与build_planner_prompt类似但不需要current_mind参数
允许与submind的思考过程并行执行
参数:
is_group_chat: 是否为群聊
chat_target_info: 目标聊天信息
cycle_history: 循环历史
observed_messages_str: 观察到的消息
structured_info: 结构化信息字符串
current_available_actions: 当前可用的动作
返回:
str: 规划器提示词
"""
try:
# --- Determine chat context ---
chat_context_description = "你现在正在一个群聊中"
chat_target_name = None # Only relevant for private
if not is_group_chat and chat_target_info:
chat_target_name = (
chat_target_info.get("person_name") or chat_target_info.get("user_nickname") or "对方"
)
chat_context_description = f"你正在和 {chat_target_name} 私聊"
# --- End determining chat context ---
# Structured info block
structured_info_block = ""
if structured_info:
structured_info_block = f"以下是一些额外的信息:\n{structured_info}\n"
# Chat content block
chat_content_block = ""
if observed_messages_str:
# Use triple quotes for multi-line string literal
chat_content_block = f"""观察到的最新聊天内容如下:
---
{observed_messages_str}
---"""
else:
chat_content_block = "当前没有观察到新的聊天内容。\\n"
# Current mind block (并行模式专用)
current_mind_block = ""
# Cycle info block (using passed cycle_history)
cycle_info_block = ""
recent_active_cycles = []
for cycle in reversed(cycle_history):
if cycle.action_taken:
recent_active_cycles.append(cycle)
if len(recent_active_cycles) == 3:
break
consecutive_text_replies = 0
responses_for_prompt = []
for cycle in recent_active_cycles:
if cycle.action_type == "text_reply":
consecutive_text_replies += 1
response_text = cycle.response_info.get("response_text", [])
formatted_response = "[空回复]" if not response_text else " ".join(response_text)
responses_for_prompt.append(formatted_response)
else:
break
if consecutive_text_replies >= 3:
cycle_info_block = f'你已经连续回复了三条消息(最近: "{responses_for_prompt[0]}",第二近: "{responses_for_prompt[1]}",第三近: "{responses_for_prompt[2]}")。你回复的有点多了,请注意'
elif consecutive_text_replies == 2:
cycle_info_block = f'你已经连续回复了两条消息(最近: "{responses_for_prompt[0]}",第二近: "{responses_for_prompt[1]}"),请注意'
elif consecutive_text_replies == 1:
cycle_info_block = f'你刚刚已经回复一条消息(内容: "{responses_for_prompt[0]}"'
if cycle_info_block:
cycle_info_block = f"\n【近期回复历史】\n{cycle_info_block}\n"
else:
cycle_info_block = "\n【近期回复历史】\n(最近没有连续文本回复)\n"
individuality = Individuality.get_instance()
prompt_personality = individuality.get_prompt(x_person=2, level=2)
action_options_text = "当前你可以选择的行动有:\n"
action_keys = list(current_available_actions.keys())
for name in action_keys:
desc = current_available_actions[name]
action_options_text += f"- '{name}': {desc}\n"
example_action_key = action_keys[0] if action_keys else "no_reply"
planner_prompt_template = await global_prompt_manager.get_prompt_async("planner_prompt")
prompt = planner_prompt_template.format(
bot_name=global_config.BOT_NICKNAME,
prompt_personality=prompt_personality,
chat_context_description=chat_context_description,
structured_info_block=structured_info_block,
chat_content_block=chat_content_block,
current_mind_block=current_mind_block,
cycle_info_block=cycle_info_block,
action_options_text=action_options_text,
example_action=example_action_key,
)
return prompt
except Exception as e:
logger.error(f"[PromptBuilder] 构建并行 Planner 提示词时出错: {e}")
logger.error(traceback.format_exc())
return "[构建并行 Planner Prompt 时出错]"
init_prompt()
prompt_builder = PromptBuilder()

View File

@@ -13,27 +13,28 @@ from typing import List, Dict
logger = get_logger("memory_activator")
Prompt(
"""
def init_prompt():
# --- Group Chat Prompt ---
memory_activator_prompt = """
你是一个记忆分析器,你需要根据以下信息来进行会议
以下是一场聊天中的信息,请根据这些信息,总结出几个关键词作为记忆回忆的触发词
{obs_info_text}
请输出一个json格式包含以下字段
{
{{
"keywords": ["关键词1", "关键词2", "关键词3",......]
}
}}
不要输出其他多余内容只输出json格式就好
""",
"memory_activator_prompt",
)
"""
Prompt(memory_activator_prompt, "memory_activator_prompt")
class MemoryActivator:
def __init__(self):
self.summary_model = LLMRequest(
model=global_config.llm_observation, temperature=0.7, max_tokens=300, request_type="chat_observation"
model=global_config.llm_summary, temperature=0.7, max_tokens=300, request_type="chat_observation"
)
self.running_memory = []
@@ -58,7 +59,10 @@ class MemoryActivator:
elif isinstance(observation, HFCloopObservation):
obs_info_text += observation.get_observe_info()
prompt = global_prompt_manager.format_prompt("memory_activator_prompt", obs_info_text=obs_info_text)
prompt = await global_prompt_manager.format_prompt(
"memory_activator_prompt",
obs_info_text=obs_info_text,
)
logger.debug(f"prompt: {prompt}")
@@ -66,7 +70,9 @@ class MemoryActivator:
logger.debug(f"response: {response}")
keywords = get_keywords_from_json(response)
# 只取response的第一个元素字符串
response_str = response[0]
keywords = list(get_keywords_from_json(response_str))
# 调用记忆系统获取相关记忆
related_memory = await HippocampusManager.get_instance().get_memory_from_topic(
@@ -75,9 +81,25 @@ class MemoryActivator:
logger.debug(f"获取到的记忆: {related_memory}")
# 激活时所有已有记忆的duration+1达到3则移除
for m in self.running_memory[:]:
m['duration'] = m.get('duration', 1) + 1
self.running_memory = [m for m in self.running_memory if m['duration'] < 4]
if related_memory:
for topic, memory in related_memory:
self.running_memory.append({"topic": topic, "content": memory, "timestamp": datetime.now().isoformat()})
logger.debug(f"添加新记忆: {topic} - {memory}")
# 检查是否已存在相同topic和content的记忆
exists = any(m['topic'] == topic and m['content'] == memory for m in self.running_memory)
if not exists:
self.running_memory.append({
"topic": topic,
"content": memory,
"timestamp": datetime.now().isoformat(),
"duration": 1
})
logger.debug(f"添加新记忆: {topic} - {memory}")
return self.running_memory
init_prompt()