Commit Graph

1 Commits

Author SHA1 Message Date
9346fed0d9 feat(webui): 星图跟随 agent 活动 + 搬到主页 + 修分类配色从未生效
星图此前只是静态展示:starmapAnimate() 只转星空,节点完全静止,
与 agent 的动作零关联。本轮三件事。

★ 修一个从未被发现的 bug:分类配色一直是坏的
  服务端 type 是首字母大写("Concept",见 internal/memory/graph.go),
  而 smTypeColors 的键全是小写 ⇒ 永远匹配不上 ⇒ 1151 个节点全渲染成
  同一个灰色 0xcccccc。浏览器实测确认:改前 colors=["cccccc"],
  改后 ["44ff88"](概念绿)。

一、跟随 agent 动(三路信号,全部在渲染循环里推进,不另起定时器)
  1. tool_call / stage / agent_output 的 SSE 事件 → 命中节点发光冲高
     + 尺寸微扩。工具名按**词**匹配实体(knowledge_list → knowledge_*)。
  2. /runtime 调度器(3s)→ 排队/中断/挂起时全图绷紧;中断或抢占计数
     上升时来一记强脉冲。
  3. /memory/graph/pulse(10s,新端点)→ 新记忆「生长」:从 0 弹到
     正常大小并留余晖。
  另:距上次活动越近,全图越亮(抽样呼吸)—— agent 一忙图就活。

二、搬到主页 + 独立页签
  总览页内嵌 360px 星图;顶部导航加「星图」独立页签(全高 + 图例)。
  同一套 renderer 用 appendChild 在容器间搬运 canvas(three.js 的
  canvas 只能有一个父节点,同时渲染会一边黑屏)。

三、性能:保留全部 1151 节点,但全部降规格
  改前每节点 = 独立 SphereGeometry(16,12) + 独立光晕球 + 一张 256x64
  CanvasTexture ⇒ 2302 个独立 geometry、约 88 万三角形、1151 个
  <canvas>,仅文字贴图就吃约 72MB 显存。全景远看根本读不清那些标签。
  改后:共享 SphereGeometry(8,6)(约 84 三角形/节点);标签改为 hover
  时在容器角上显示 HTML 文本(零显存,且比 3D 贴图更清晰);
  866 条边按关系类型合并成 4 个 LineSegments(draw call 866 → 4)。
  hover 复位随之改为 baseScale —— 旧的 set(1,1,1) 会把按 mention_count
  缩放过的大节点缩成最小尺寸。

四、/memory/graph 瘦身:不再下发稠密向量
  星图是本接口唯一消费者,却从不读 vector。生产实测该字段占
  79,314 / 402,811 字节 = 19%,而 8 块记忆就这么多,200 块就是 ~2MB
  白查白发白堆。真实数据集实测响应 402,811 → 326,997 字节(-18%)。

新增 /memory/graph/pulse:只回 since 窗口内变动过的实体(id/name/type/
mention_count/updated_at)。星图每 10s 拉它来判断「哪个节点新长出来」,
而不必重拉 400KB 全量。

验证(不是「应该能跑」):
  - go vet 干净;go test 全绿;新增 5 个测试(向量裁剪 / pulse 窗口 /
    since 放大 / pulse 不带向量 / 类型断言失败时透传不丢数据)
  - 覆盖率 65.5% → 66.5%
  - 真实 1151 节点数据集上跑 headless chromium + SwiftShader 实测:
    nodeMeshes=1151、edgeSegs=4、geoShared=true、控制台零报错、
    图例与统计(1151 节点 / 866 关系)正常、canvas 在两个容器间正确搬运
  - 脉冲匹配在浏览器里逐个 hint 验证:
      knowledge_list → 2 个(只命中 knowledge_base / knowledge_list)
      qq_get_message 等无匹配 → 8 个(走「整体活动」兜底)
    ★ 途中修掉自己的两个错:① 最早的子串匹配让 hint="knowledge" 命中
    全部单字实体(一次 pulse 选中 250 个、队列顶到 260 上限);
    ② 改成词匹配后,旧的「补齐到 20 个」逻辑又把 1 个真实命中补成 20 个
    无关节点 —— 现象与①一样,只是成因不同。补齐现在只在**完全无匹配**
    时启用。

未做(本轮范围外):服务端 gzip(首屏 793KB 无压缩,实测可压到 ~240KB)、
renderAll 按页签懒加载(首屏仍在拉隐藏页签的 kernel+settings 共 230KB)、
setInterval 15s 全量重拉(空闲 53MB/h)。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-09-26 23:31:58 +08:00