Skip to content

fix(store): 同步清理 TTL 过期记录的 FTS 索引#491

Open
Qiyuanqiii wants to merge 1 commit into
TencentCloud:mainfrom
Qiyuanqiii:fix/issue-160-ttl-fts-ghosts
Open

fix(store): 同步清理 TTL 过期记录的 FTS 索引#491
Qiyuanqiii wants to merge 1 commit into
TencentCloud:mainfrom
Qiyuanqiii:fix/issue-160-ttl-fts-ghosts

Conversation

@Qiyuanqiii

@Qiyuanqiii Qiyuanqiii commented Jul 13, 2026

Copy link
Copy Markdown

关联 Issue

Related to #160

背景与定位

#160 的标准窄范围修复已经由 #178 负责,其他相关增量也有明确边界:

本 PR 不修改查询构造或 tokenizer,而是修复 SQLite 存储层另一条独立的一致性问题:TTL 已删除的记忆仍残留在 FTS 表中,并可继续被关键词搜索召回。

问题根因

deleteL1Expired()deleteL0Expired() 的事务当前只清理两类数据:

  • l1_records / l0_conversations 主表记录
  • l1_vec / l0_vec 向量记录

l1_ftsl0_fts 是独立的 FTS5 虚拟表,不会随着主表删除自动级联。关键词搜索又直接读取 FTS 表,因此 TTL 清理完成后,已过期内容仍可能作为“幽灵索引”返回。

真实复现中,L1/L0 主表均从 5 条降至 4 条,但已删除的 l1-0l0-0 仍分别出现在 FTS 查询结果中。这不仅影响召回正确性,也违背 TTL 的数据保留语义。

实现方案

  • 为 L1 与 L0 分别增加 TTL FTS 删除预编译语句
  • 使用主表中与现有 TTL 条件完全相同的 cutoff 筛选过期 record ID
  • 在删除主表记录前先删除对应 FTS 行,确保子查询仍能读取权威 record ID
  • 将 FTS、向量表与主表删除放入现有同一事务
  • FTS 删除失败时触发现有回滚路径,不提交半完成的 TTL 清理
  • 新增真实 SQLite FTS5 回归测试,同时覆盖 L1 与 L0

兼容性

未启用 FTS5 时继续沿用原有 TTL 清理路径。启用 FTS5 时,只删除已经被同一 cutoff 判定为过期的索引行。

本 PR 保留:

  • 现有单次删除不得超过总记录数 80% 的保护
  • 原有 L1 updated_time 与 L0 recorded_at 过期语义
  • 普通写入、单条删除、批量删除及关键词排序行为
  • FTS 不可用时的降级行为

本 PR 不包含:

  • FTS5 查询运算符净化
  • tokenizer 或 MATCH 表达式调整
  • 启动期全量索引重建
  • TCVDB 后端清理语义修改
  • 新的公开配置项或数据库 schema 版本

因此它是 SQLite TTL 事务的索引同步修复,不替代 #178#484

验证

  • 定向测试:1 个文件、2 项测试通过
  • 完整测试:5 个文件、69 项测试通过
  • 插件及三个脚本构建:通过
  • git diff --check:通过
npm test -- src/core/store/fts-expiry-sync.test.ts --reporter=verbose
npm test
npm run build
git diff --check origin/main...HEAD

定向测试覆盖

  • TTL 清理前,过期 L1 记录可以通过 FTS 命中
  • TTL 清理后,L1 主表计数减少且过期记录不再被 FTS 召回
  • TTL 清理前,过期 L0 记录可以通过 FTS 命中
  • TTL 清理后,L0 主表计数减少且过期记录不再被 FTS 召回
  • 未过期的 L1/L0 记录仍可正常关键词检索
  • 使用 5 条记录清理其中 1 条,覆盖并保留现有 80% 比例保护

验证截图

image

@Maxwell-Code07

Copy link
Copy Markdown
Collaborator

Thank you for submitting this PR and participating in Tencent Rhino-bird Open-source Training Program!
We have successfully received your submission. The program is currently in full swing, and we will complete the Code Review for you as soon as possible. Please keep an eye on the status notifications for this PR so you can follow up promptly once the review feedback is provided.
Thanks again for your contribution and open-source spirit! 🚀

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants