Files
uncle6me-web 962d863ef7 fix(kbdb): 藏書地圖 M3 收尾——讀端自動核對重算,不再依賴 ingest 接鏈
真因(總管實測,system-dev/wiki/mistakes.md 08-08 段):design 原訂「ingest 尾端呼
POST /map/recompute」,但 repo 內查無任何呼叫點,三週沒接上,沒手動 backfill 過的租戶
(絕大多數)GET /map 恆回空;MCP 說明文字還宣稱「地圖由 ingest 尾端自動重算(M3)」——假話。

leo 否決「降級成即時聚合、不維護快取」的提案(會丟失 narrative 這類摘要本體,只算得出
count)。改法:GET /map/GET /map/:library 讀端自己核對即時三元組數,落差就地呼叫既有的
recomputeLibraryMap 補算(kbdb/src/actions/library-map.ts ensureFreshLibraryMaps)。聚合
SQL 沒有第二套、narrative/relation_profile/bridges 摘要欄位原封不動,只是觸發時機從「等
外部呼叫」改成「讀的當下順手核對」。同時解掉:全租戶自動 backfill/跟得上新資料/不依賴
跨 repo 的 ingest 接鏈。

附帶修 recomputeLibraryMap 的 narrative 欄位:沒帶值時原本會清空,改成沿用上一版(避免
自動重算把 ingest 端/人工填過的 narrative 靜默洗掉)。

修正三處說謊的說明文字(mcp/src/tools/kbdb_map.ts、console-ui console/index.html):
「地圖由 ingest 尾端自動重算(M3)」不存在,改為誠實描述讀端即時核對機制;404 語意從
「從未 recompute」改為「查無此庫」(已知但空的庫現在會自動補成 triplet_count:0 的 200,
不會落到 404)。

測試:kbdb 新增 6 案(18/18 全綠,覆蓋自動 backfill/跟得上資料/narrative 保留/
404 vs 空庫誠實分辨/owner 隔離/無 triplet template 不報錯);mcp 新增 1 案釘住舊謊言
不再出現。kbdb 125/125、mcp 69/77(同基線 8 個 oauth 既有失敗,非本次引入)全綠;
tsc 兩包乾淨(kbdb 1 個既有 auth.test.ts 錯誤與 stash 前一致,非本次引入)。

SDD:system-dev/docs/3-specs/library-map/tasks.md M3 從「07-19 誤標 」更正為實況;
design.md §3 加 2026-08-08 更正說明。未動 frontmatter status(仍 draft,D35 生命週期
鐵律留給總管/leo 裁)。

殘項:本次修改只在本機驗證(真 SQLite + 假 binding 單元測試),未部署 prod;未在真實
KBDB(如 yuga3bse 租戶)重新實測 kbdb_get_map 非空——需部署後才能貼實測輸出。

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-08 00:44:55 +08:00

5.3 KiB
Raw Permalink Blame History

status, note
status note
draft leo 2026-07-19「藏書地圖可以走」=design confirmed 可動工(M1/M2 起跑);active 標記待對照 Arcrun 現行 active SDD 收斂。

library-map(藏書地圖)— Design

1. 資料結構:library_map Template(照 leo spec §3

每庫一個 map block。slotslibrary(text)narrative(text,抽自該庫頂層 wiki 首段)/top_entities(arraydegree 排序 top-N)relation_profile(arraypredicate 分布=庫的性格)bridges(array,同 entity 跨庫 join)triplet_count(number)commit_hash(text)status(active|superseded)。

三元組按庫過濾:先核實現況——rag-ingest-cards v2 的 triplet 已帶 source_uri、entries 已有 metadata.libraryportal-auth P1);若 triplet 定位庫仍不足,在 Triplet Template schema 加 optional library slot(改 template 不動表)。

核實結果(2026-07-19M1 對 prod 實查)triplet templateprod 名 triplet,非 MCP 註解寫的 graph_tripletslotssubject/predicate/object/…/source_uri/…,library slotentries 的 metadata.library 機制在但既有資料未標記(?library=kb → 0 筆)→ 定位庫不足,走預案M1 於 recompute 時冪等地在 triplet template 加 optional library slotensureTripletLibrarySlot,改 template 不動表);slot 值由 ingest 端補寫(M3)。過渡期 /map/recompute 收 optional source_prefix 參數,對「無 library 值的舊 triplet」以 source_uri 前綴歸庫(如 gitea:Leo/kb@)——前綴由 caller 提供,base 不寫死 URI 語意;bridges 的「對面庫」只認 library slot 標記值,M3 backfill 前會偏稀疏(誠實限制)。

2. 重算的家:SQL 只能住基本盤(D6 推論,本 SDD 關鍵歸屬裁定)

degree 排序/predicate 統計/跨庫 join 是聚合 SQL——D6 鐵律:插件與 workflow 全程禁 SQL。故重算實作=kbdb base 新增內建端點 POST /map/recompute?library=(基本盤內 SQL 合法,一段交易:算→建新 block→舊標 superseded)。ingest workflowA 類)尾端用 http_request 呼此端點——A 類接 B 類 API,牆不破。 讀取端點 GET /map(全館,每庫一行)/GET /map/:library(詳圖),MCP/GUI 共用。

3. 更新機制(leo spec §4

ingest 完成 → 取本次 commit diff 涉及的庫集合 → 逐庫呼 /map/recompute。無 cron 全量。首次 backfill=對每個既有庫手動各呼一次(installer/腳本一行)。

2026-08-08 更正(matrix/arcrun CC:上面這條「ingest 尾端接鏈」的路徑本身沒錯(arcrun-rag 那條管線也確實接了,670f38a),但它只覆蓋接了鏈的那一條 ingest——這個 repo 內(kbdb/ cypher-executor/mcp)從沒有任何呼叫點會打 /map/recompute,導致沒手動 backfill 過的租戶 (絕大多數)恆空,且拖了三週沒人發現/接上(見 system-dev/wiki/mistakes.md 08-08 段)。 改法(leo 否決「降級成即時聚合、不維護快取」的提案,因為那會丟失 narrative 這類摘要 本體):GET /mapGET /map/:library 讀端自己核對即時三元組數,落差就地呼叫既有的 recomputeLibraryMap 補算(kbdb/src/actions/library-map.ts ensureFreshLibraryMaps)。 聚合 SQL 仍只住 kbdb base(沒有違反 §2 的歸屬裁定),只是觸發時機從「等外部呼叫」改成 「讀的當下順手核對」——這條讀端機制本身就是「無 cron 全量」的自動 backfill,取代了 「首次 backfill=對每個既有庫手動各呼一次」這句手動步驟。細節見 system-dev/docs/3-specs/library-map/tasks.md M3 段。

4. 注入(leo spec §5,本功能重點)

  • MCP instructionsarcrun-mcp 啟動組 instructions 時拉 GET /map 嵌入(快取+TTL,或每次連線現拉——量數百 token,現拉可接受)。
  • get_map 工具:薄殼呼 /map/map/:library。與 #68 的 kbdb_graph_neighbors 同族(D17 KBDB MCP 面),可同 PR 或緊接。
  • GUIconsole/portal 首頁 render GET /map——庫卡片(narrativetop entities+規模)+跨庫 bridges 一覽;點庫進該庫搜尋。

5. 與 D30 檢索治本的連動(本 SDD 新增,超出原 spec)

leo 終景「補充的只 vectorize entities+一句話」與本件是同一素材的兩用:map block 的 narrativetop_entities=卡級/庫級摘要嵌入單位。落法:map block 的 content 欄寫成可嵌人話({library}{narrative}。核心:{top_entities}),標 embed → semantic 第一跳打 map 層做庫路由,第二跳才進庫內(D30「向量做路由、定稿給 LLM 讀」)。#58/#59 的殘影/模型問題在 map 層天然緩解(block 少、可整層重刷)。

6. Retrieval 流程(改造後,leo spec §6 原文)

session 啟動 → instructions 已含全館地圖(push 零查詢)→ 需細節 get_map(library) → graph query 找 entity/關係 → 依 index 取 repo wiki 定稿(真相源不變)。

7. 歸屬

kbdb base 端點=B 類(PR);ingest 尾端接鏈=A 類(workflow 改版,arcrun-rag/個人庫同款);MCPB 類;GUI=B 類(console 路由)。全框架件:寫一次,arcrun-rag/Mira/未來客戶全實例受益(bundle 更新分發)。