Files
zqf b1f93588f1 初始化:记忆系统源代码上传(已脱敏)
- 排除 .env / *.bak / 内部运维文档(README_INTERNAL.html)
- config.py 默认密码已替换为占位符 CHANGE_ME_*
- init_db.sql 移除生产数据库用户 GRANT 段
- README.html 数据库用户名已脱敏
- 保留:源码 + 公网 API 文档 + 建表 SQL(无授权语句)
2026-08-03 04:53:48 +08:00

81 lines
3.1 KiB
Python

"""Persona Generator - Generate user persona from scenarios and memories."""
import json
import logging
from typing import Optional
from lifecycle.llm_parse import parse_llm_json_object
logger = logging.getLogger(__name__)
PERSONA_SYSTEM_PROMPT = """你是JSON生成器。直接输出JSON对象,禁止分析、思考、解释、markdown。
根据记忆和场景生成用户画像。
输出格式(第一个字符必须是{,最后一个字符必须是}):
{"preferences":["偏好1"],"habits":["习惯1"],"expertise":["擅长1"],"communication_style":"风格","summary":"100字以内摘要"}
只输出JSON,不要有任何其他文字。"""
class PersonaGenerator:
"""Generate user persona from memories and scenarios."""
def __init__(self, mysql_store, llm_client):
self.mysql = mysql_store
self.llm = llm_client
def generate(self, agent_id: str, team_id: str,
max_items: int = 30) -> dict:
if not self.llm.available:
return {"error": "LLM not configured. Set LLM_API_URL, LLM_API_KEY, LLM_MODEL environment variables."}
memories = self.mysql.get_personal_memories_by_agent(agent_id, limit=max_items)
scenarios = self.mysql.get_scenarios_by_agent(agent_id)
if not memories and not scenarios:
return {"error": "No memories or scenarios found for this agent"}
context_parts = []
if memories:
mem_lines = [f"- {m.get('content', '')[:100]}" for m in memories]
context_parts.append("历史记忆:\n" + "\n".join(mem_lines))
if scenarios:
scene_lines = [f"- [{s.get('name', '')}] {s.get('summary', '')}" for s in scenarios]
context_parts.append("已识别场景:\n" + "\n".join(scene_lines))
user_prompt = "请根据以下内容生成用户画像JSON:\n\n" + "\n\n".join(context_parts)
try:
persona = parse_llm_json_object(
self.llm, PERSONA_SYSTEM_PROMPT, user_prompt,
temperature=0.3, context="generate-persona",
max_tokens=2000,
)
except ValueError as e:
return {"error": str(e)}
if not isinstance(persona, dict):
logger.warning("LLM returned non-dict persona: %r", persona)
return {"error": "LLM returned invalid persona format"}
pid = self.mysql.add_persona(
team_id=team_id,
agent_id=agent_id,
preferences=persona.get("preferences", []),
habits=persona.get("habits", []),
expertise=persona.get("expertise", []),
communication_style=persona.get("communication_style", ""),
summary=persona.get("summary", ""),
)
persona["id"] = pid
return {"persona": persona}
def get_persona(self, agent_id: str):
return self.mysql.get_persona_by_agent(agent_id)
def delete_persona(self, persona_id: str, team_id: str) -> bool:
persona = self.mysql.get_persona(persona_id)
if not persona or persona["team_id"] != team_id:
return False
return self.mysql.delete_persona(persona_id)