# -*- coding: utf-8 -*- import json from typing import Dict, List class MemberContextPromptBuilder: """成员分层画像提示词构建器""" @staticmethod def build_daily_digest_prompt(chatroom_id: str, wxid: str, display_name: str, digest_date: str, messages: List[Dict]) -> str: lines = [] for msg in messages[-80:]: ts = str(msg.get("timestamp", ""))[11:16] content = (msg.get("content") or "").replace("\n", " ").strip()[:180] if content: lines.append(f"[{ts}] {content}") return ( "你是微信群后台的成员日观察摘要生成器。\n" "请仅基于给定的当日公开聊天记录,提取对后续互动有帮助的中性行为观察。\n" "不要做人格诊断、隐私猜测、负面评价,不要脑补群外信息。\n" "输出严格 JSON,不要 markdown。\n" "{" "\"topics\":[\"主题1\"]," "\"interaction_style\":\"一句中文\"," "\"message_pattern\":\"一句中文\"," "\"response_style_hint\":\"一句中文\"," "\"habit_signals\":[\"信号1\"]," "\"engagement_traits\":[\"特征1\"]," "\"reply_taboos\":[\"避坑1\"]," "\"temperament_signal\":\"一句中文,描述当天显露的沟通倾向,必须克制\"," "\"summary_text\":\"一段不超过100字的日摘要\"," "\"representative_messages\":[\"原话1\",\"原话2\"]," "\"confidence\":0.0" "}\n" "要求:\n" "1. topics 最多4个,habit_signals 最多4个,engagement_traits 最多4个,reply_taboos 最多3个。\n" "2. temperament_signal 只能写当日可观察到的沟通倾向,不可上升为长期性格判断。\n" "3. representative_messages 保留最能代表当天风格的短句,最多3条。\n" f"成员: {display_name} ({wxid})\n" f"群ID: {chatroom_id}\n" f"日期: {digest_date}\n" "当日消息:\n" + ("\n".join(lines) or "暂无") ) @staticmethod def build_period_digest_prompt(digest_type: str, chatroom_id: str, wxid: str, display_name: str, period_key: str, items: List[Dict]) -> str: structured_lines = [] for item in items: structured = item.get("structured", {}) or {} payload = { "period_key": item.get("period_key"), "summary_text": item.get("summary_text", ""), "topics": structured.get("topics") or structured.get("stable_topics") or structured.get("long_term_topics") or [], "habit_signals": structured.get("habit_signals") or structured.get("habit_patterns") or [], "engagement_traits": structured.get("engagement_traits") or structured.get("stable_traits") or [], "reply_preferences": structured.get("reply_preferences") or structured.get("long_term_reply_preferences") or [], "temperament_signal": structured.get("temperament_signal") or structured.get("temperament_tendency") or "", "recent_state": structured.get("recent_state") or [], } structured_lines.append(json.dumps(payload, ensure_ascii=False)) if digest_type == "weekly": schema = ( "{" "\"stable_topics\":[\"主题1\"]," "\"stable_traits\":[\"特征1\"]," "\"habit_patterns\":[\"习惯1\"]," "\"reply_preferences\":[\"偏好1\"]," "\"recent_state\":[\"状态1\"]," "\"temperament_tendency\":\"一句中文\"," "\"summary_text\":\"一段不超过120字的周摘要\"," "\"confidence\":0.0" "}" ) extra = "请从多个日摘要中提炼本周重复出现的模式,过滤单日噪音。" else: schema = ( "{" "\"long_term_topics\":[\"主题1\"]," "\"stable_traits\":[\"特征1\"]," "\"habit_patterns\":[\"习惯1\"]," "\"long_term_reply_preferences\":[\"偏好1\"]," "\"phase_state\":[\"状态1\"]," "\"temperament_tendency\":\"一句中文\"," "\"summary_text\":\"一段不超过140字的月摘要\"," "\"confidence\":0.0" "}" ) extra = "请从多个周摘要中提炼阶段性稳定特征,只有反复出现的模式才能进入长期层。" return ( f"你是微信群后台的成员{digest_type}摘要生成器。\n" f"{extra}\n" "不可做心理诊断、负面评价、隐私猜测。输出严格 JSON,不要 markdown。\n" f"{schema}\n" "要求:\n" "1. 所有列表字段最多5项,必须中性克制。\n" "2. 只有多个下级摘要反复出现的特征,才允许写进 stable_traits / habit_patterns / long_term_reply_preferences。\n" "3. recent_state / phase_state 只描述当前阶段状态,不要冒充长期人格。\n" f"成员: {display_name} ({wxid})\n" f"群ID: {chatroom_id}\n" f"周期: {period_key}\n" "下级摘要:\n" + ("\n".join(structured_lines) or "暂无") ) @staticmethod def build_final_context_prompt(chatroom_id: str, wxid: str, display_name: str, monthly_digests: List[Dict], weekly_digests: List[Dict], daily_digests: List[Dict]) -> str: monthly_lines = [json.dumps(item.get("structured", {}), ensure_ascii=False) for item in monthly_digests[:6]] weekly_lines = [json.dumps(item.get("structured", {}), ensure_ascii=False) for item in weekly_digests[:4]] daily_lines = [json.dumps(item.get("structured", {}), ensure_ascii=False) for item in daily_digests[:6]] return ( "你是微信群后台的最终成员交互画像整理器。\n" "请结合月级、周级、日级摘要,输出一个既有长期层又有近期层的后台交互画像。\n" "不要做敏感推断、心理诊断、隐私猜测。输出严格 JSON,不要 markdown。\n" "{" "\"activity_level\":\"高活跃|中活跃|低活跃|观察中\"," "\"message_pattern\":\"一句中文\"," "\"interaction_style\":\"一句中文\"," "\"response_style_hint\":\"一句中文\"," "\"topics_of_interest\":[\"主题1\"]," "\"recent_focus\":[\"近期主题1\"]," "\"stable_traits\":[\"长期特征1\"]," "\"habit_patterns\":[\"习惯1\"]," "\"long_term_reply_preferences\":[\"偏好1\"]," "\"recent_state\":[\"近期状态1\"]," "\"temperament_tendency\":\"一句中文\"," "\"summary_text\":\"一段不超过150字的后台摘要\"," "\"confidence\":0.0," "\"engagement_traits\":[\"特征1\"]," "\"reply_taboos\":[\"避坑1\"]" "}\n" "要求:\n" "1. stable_traits、habit_patterns、long_term_reply_preferences 只从月级和多次重复证据中提取。\n" "2. recent_focus、recent_state 更依赖最近周级和日级。\n" "3. summary_text 要像后台备注,不要明显暴露在给用户做画像。\n" f"成员: {display_name} ({wxid})\n" f"群ID: {chatroom_id}\n" "月级摘要:\n" + ("\n".join(monthly_lines) or "暂无") + "\n周级摘要:\n" + ("\n".join(weekly_lines) or "暂无") + "\n日级摘要:\n" + ("\n".join(daily_lines) or "暂无") )