feat(memory): 实现瞬时记忆系统的延迟加载和按需初始化

引入了对LLM和向量瞬时记忆系统的延迟初始化机制。现在,只有在实际需要存储或检索记忆时,才会触发相应记忆系统的初始化过程。

此项改动优化了应用的启动性能,避免了不必要的资源预加载。同时,新增了独立的配置开关,允许用户根据需求分别启用或禁用LLM和向量记忆模块,提供了更灵活的配置选项。
This commit is contained in:
minecraft1024a
2025-08-22 14:07:49 +08:00
parent 60eaef6b20
commit d67a831eb4
3 changed files with 53 additions and 34 deletions

View File

@@ -22,27 +22,32 @@ class AsyncInstantMemoryWrapper:
self.cache: Dict[str, tuple[Any, float]] = {} # 缓存:(结果, 时间戳)
self.cache_ttl = 300 # 缓存5分钟
self.default_timeout = 3.0 # 默认超时3秒
# 延迟加载记忆系统
self._initialize_memory_systems()
def _initialize_memory_systems(self):
"""延迟初始化记忆系统"""
try:
# 初始化LLM记忆系统
from src.chat.memory_system.instant_memory import InstantMemory
self.llm_memory = InstantMemory(self.chat_id)
logger.debug(f"LLM瞬时记忆系统已初始化: {self.chat_id}")
except Exception as e:
logger.warning(f"LLM瞬时记忆系统初始化失败: {e}")
try:
# 初始化向量记忆系统
from src.chat.memory_system.vector_instant_memory import VectorInstantMemoryV2
self.vector_memory = VectorInstantMemoryV2(self.chat_id)
logger.debug(f"向量瞬时记忆系统已初始化: {self.chat_id}")
except Exception as e:
logger.warning(f"向量瞬时记忆系统初始化失败: {e}")
# 从配置中读取是否启用各种记忆系统
self.llm_memory_enabled = global_config.memory.enable_llm_instant_memory
self.vector_memory_enabled = global_config.memory.enable_vector_instant_memory
async def _ensure_llm_memory(self):
"""确保LLM记忆系统已初始化"""
if self.llm_memory is None and self.llm_memory_enabled:
try:
from src.chat.memory_system.instant_memory import InstantMemory
self.llm_memory = InstantMemory(self.chat_id)
logger.debug(f"LLM瞬时记忆系统已初始化: {self.chat_id}")
except Exception as e:
logger.warning(f"LLM瞬时记忆系统初始化失败: {e}")
self.llm_memory_enabled = False # 初始化失败则禁用
async def _ensure_vector_memory(self):
"""确保向量记忆系统已初始化"""
if self.vector_memory is None and self.vector_memory_enabled:
try:
from src.chat.memory_system.vector_instant_memory import VectorInstantMemoryV2
self.vector_memory = VectorInstantMemoryV2(self.chat_id)
logger.debug(f"向量瞬时记忆系统已初始化: {self.chat_id}")
except Exception as e:
logger.warning(f"向量瞬时记忆系统初始化失败: {e}")
self.vector_memory_enabled = False # 初始化失败则禁用
def _get_cache_key(self, operation: str, content: str) -> str:
"""生成缓存键"""
@@ -67,17 +72,16 @@ class AsyncInstantMemoryWrapper:
"""缓存结果"""
self.cache[cache_key] = (result, time.time())
async def store_memory_async(self, content: str, timeout: float = None) -> bool:
async def store_memory_async(self, content: str, timeout: Optional[float] = None) -> bool:
"""异步存储记忆(带超时控制)"""
if timeout is None:
timeout = self.default_timeout
success_count = 0
total_systems = 0
# 异步存储到LLM记忆系统
await self._ensure_llm_memory()
if self.llm_memory:
total_systems += 1
try:
await asyncio.wait_for(
self.llm_memory.create_and_store_memory(content),
@@ -91,8 +95,8 @@ class AsyncInstantMemoryWrapper:
logger.error(f"LLM记忆存储失败: {e}")
# 异步存储到向量记忆系统
await self._ensure_vector_memory()
if self.vector_memory:
total_systems += 1
try:
await asyncio.wait_for(
self.vector_memory.store_message(content),
@@ -107,7 +111,7 @@ class AsyncInstantMemoryWrapper:
return success_count > 0
async def retrieve_memory_async(self, query: str, timeout: float = None,
async def retrieve_memory_async(self, query: str, timeout: Optional[float] = None,
use_cache: bool = True) -> Optional[Any]:
"""异步检索记忆(带缓存和超时控制)"""
if timeout is None:
@@ -125,6 +129,7 @@ class AsyncInstantMemoryWrapper:
results = []
# 从向量记忆系统检索(优先,速度快)
await self._ensure_vector_memory()
if self.vector_memory:
try:
vector_result = await asyncio.wait_for(
@@ -140,6 +145,7 @@ class AsyncInstantMemoryWrapper:
logger.error(f"向量记忆检索失败: {e}")
# 从LLM记忆系统检索备用更准确但较慢
await self._ensure_llm_memory()
if self.llm_memory and len(results) == 0: # 只有向量检索失败时才使用LLM
try:
llm_result = await asyncio.wait_for(

View File

@@ -13,6 +13,7 @@ import threading
from concurrent.futures import ThreadPoolExecutor
from src.common.logger import get_logger
from src.config.config import global_config
from src.chat.memory_system.async_instant_memory_wrapper import get_async_instant_memory
logger = get_logger("async_memory_optimizer")
@@ -140,11 +141,16 @@ class AsyncMemoryQueue:
# 这里需要根据具体的记忆系统来实现
# 为了避免循环导入,这里使用延迟导入
try:
from src.chat.memory_system.instant_memory import InstantMemory
# 获取包装器实例
memory_wrapper = get_async_instant_memory(task.chat_id)
instant_memory = InstantMemory(task.chat_id)
await instant_memory.create_and_store_memory(task.content)
return True
# 使用包装器中的llm_memory实例
if memory_wrapper and memory_wrapper.llm_memory:
await memory_wrapper.llm_memory.create_and_store_memory(task.content)
return True
else:
logger.warning(f"无法获取记忆系统实例,存储任务失败: chat_id={task.chat_id}")
return False
except Exception as e:
logger.error(f"记忆存储失败: {e}")
return False
@@ -152,11 +158,16 @@ class AsyncMemoryQueue:
async def _handle_retrieve_task(self, task: MemoryTask) -> Any:
"""处理记忆检索任务"""
try:
from src.chat.memory_system.instant_memory import InstantMemory
# 获取包装器实例
memory_wrapper = get_async_instant_memory(task.chat_id)
instant_memory = InstantMemory(task.chat_id)
memories = await instant_memory.get_memory(task.content)
return memories or []
# 使用包装器中的llm_memory实例
if memory_wrapper and memory_wrapper.llm_memory:
memories = await memory_wrapper.llm_memory.get_memory(task.content)
return memories or []
else:
logger.warning(f"无法获取记忆系统实例,检索任务失败: chat_id={task.chat_id}")
return []
except Exception as e:
logger.error(f"记忆检索失败: {e}")
return []

View File

@@ -449,6 +449,8 @@ class MemoryConfig(ValidatedConfigBase):
consolidate_memory_percentage: float = Field(default=0.01, description="巩固记忆百分比")
memory_ban_words: list[str] = Field(default_factory=lambda: ["表情包", "图片", "回复", "聊天记录"], description="记忆禁用词")
enable_instant_memory: bool = Field(default=True, description="启用即时记忆")
enable_llm_instant_memory: bool = Field(default=True, description="启用基于LLM的瞬时记忆")
enable_vector_instant_memory: bool = Field(default=True, description="启用基于向量的瞬时记忆")