📁 修改文件清单
| 文件 |
新增内容 |
新增行数 |
hermes_state.py |
_load_vec_extension, _ensure_vec_table, store_embedding, search_by_vector, _search_by_vector_vec, _search_by_vector_python, get_unembedded_messages, embedding_count |
~260行 |
tools/session_search_tool.py |
_QueryVectorCache, _get_memory_search_config, _vector_recall, _rrf_merge + 注入到 session_search() |
~260行 |
🔧 修复的关键 Bug
sqlite-vec
KNN 查询:LIMIT ? → AND k = ?(vec0 虚拟表要求 k 参数)
🧪 验证结果
✅
hermes_state.py
语法通过 + 全部 8 个方法可用
✅
session_search_tool.py
语法通过 + 4 个向量函数可用
✅
sqlite-vec
已加载 vec_available=True
✅
embedding_count
8553条 正常运行
✅
store_embedding
双写OK (BLOB + vec_messages)
✅
search_by_vector
KNN可用 自动选择 sqlite-vec 或纯Python
🏗️ 架构全貌
用户消息 → append_message()
│
├── ① 写入 messages 表(原有)
│
└── ② daemon 线程 → _auto_embed_worker
│
├── _get_embed_config() → config.yaml
│
├── _call_embedding_api_local() → 火山API
│
└── db.store_embedding() → BLOB + vec_messages
session_search 查询时:
query
│
├──→ ① FTS5 关键词搜索 ─┐
│
└──→ ② _vector_recall() ─┤ (LRU cache 加速)
│
├→ _rrf_merge(k=60, vector_weight=1.5)
│
└→ 分组去重 → LLM总结 → 返回结果
🎉 全部 10 项测试通过!
| # |
测试项 |
结果 |
关键指标 |
| 1 | 数据库连接与表状态 | ✅ | 20,275 消息 / 8,553 向量 / 1,166 会话 |
| 2 | 核心 SessionDB 方法 | ✅ | embedding_count, get_unembedded_messages 正常 |
| 3 | store_embedding 幂等性 | ✅ | 相同文本跳过写入,不同文本触发更新 |
| 4 | Embedding API 调用 | ✅ | doubao-embedding-vision, 2048维, 379ms |
| 5 | search_by_vector (sqlite-vec) | ✅ | 返回语义相关结果, 149ms |
| 6 | 纯Python回退路径 | ✅ | 2,520ms (sqlite-vec 快 16.9x) |
| 7 | RRF 混合排序 | ✅ | hybrid > vector/fts5 单路, 排序正确 |
| 8 | Query Vector Cache (LRU) | ✅ | hit/miss/evict 全正常 |
| 9 | _vector_recall 集成 | ✅ | 首次 230ms → cache_hit 56ms (4.1x ⚡) |
| 10 | session_search 完整性 | ✅ | 全模块可导入,配置正常 |
🔬 关键发现
语义搜索示例: query="磁盘空间清理"
sim=0.8738 "磁盘空间不足如何清理?"
sim=0.8731 "磁盘空间不足如何清理?"
sim=0.8168 "Ubuntu磁盘空间分析和清理方案"
语义匹配精准:即使用词不完全匹配("磁盘空间清理" vs "磁盘空间不足如何清理"),相似度仍达 0.87
vec_messages 完全同步:8,553 = 8,553(BLOB 表与虚拟表零误差)
RRF 正确提升 hybrid 结果:B(sim=0.0164 fts5-only) → B(rrf=0.0407 hybrid) 跃居第一