- wire SQLite control-plane access/session paths into Rust web local-folder routes - preserve local Markdown attachment semantics across upload, reload, and secondary-pane resource tabs - refresh design governance docs, Reasonix task templates, and bug records - retire root .mcp.json local MCP config
420 lines
12 KiB
Markdown
420 lines
12 KiB
Markdown
# 4-3 [done] Tree-First Graph Kernel Phase 4 专项任务拆分 v1
|
||
|
||
> 更新时间:2026-04-16
|
||
>
|
||
> 关联文档:
|
||
> - `/mnt/Data1T/mnote/design/01-tree-first-graph-kernel/reference/1-tree-first-graph-kernel-v1.md`
|
||
> - `/mnt/Data1T/mnote/design/01-tree-first-graph-kernel/reference/1-1-tree-first-graph-kernel-checklist-v2.md`
|
||
> - `/mnt/Data1T/mnote/design/04-tree-domain/process/4-sidebar-pagetree-filetree-rust-web-rebuild-v1.md`
|
||
|
||
## 1. 文档目的
|
||
|
||
这份文档只处理一件事:
|
||
|
||
> **把 `Kernel Phase 4:Sidebar / 页面树 / 文件树切到 kernel projection` 单独拆开,按当前真实代码重写成可执行任务。**
|
||
|
||
这个阶段的目标不是:
|
||
|
||
- 直接重写整个 Sidebar
|
||
- 直接把树 UI 改成 `Leptos`
|
||
- 直接启动树域 Rust Web shell 替换
|
||
|
||
这个阶段只负责:
|
||
|
||
> **把树域的 truth、projection、consumer 协议先统一。**
|
||
|
||
也就是先把树“变对”,再谈“换壳”。
|
||
|
||
---
|
||
|
||
## 2. Phase 4 的准确定位
|
||
|
||
在 `tree-first graph kernel` 里:
|
||
|
||
- 树是主骨架
|
||
- 页面树 / 文件树都只是 projection
|
||
- Sidebar 是树域承载壳,不是事实源
|
||
|
||
所以 `Phase 4` 的本质不是普通前端整理,而是:
|
||
|
||
> **让树域 consumer 不再自己拼树,而是统一消费稳定的 kernel projection。**
|
||
|
||
如果这一步不先完成,后面的 Rust Web tree shell 重构就会在协议未冻结前重复返工。
|
||
|
||
---
|
||
|
||
## 3. 当前真实完成情况
|
||
|
||
基于当前 git,`Phase 4` 已经有一些关键前置。
|
||
|
||
### 3.1 已有 projection 起点
|
||
|
||
- `sidebar.dataset.list` 已能产出:
|
||
- `kernel_sidebar_projection`
|
||
- `kernelSidebarTree`
|
||
- 对应文件:
|
||
- [sidebar-data.ts](/mnt/Data1T/mnote/wolai-frontend/src/lib/sidebar-data.ts)
|
||
- [kernel-sidebar.ts](/mnt/Data1T/mnote/wolai-frontend/src/lib/kernel-sidebar.ts)
|
||
|
||
### 3.2 Sidebar 主树已切到统一 tree consumer
|
||
|
||
- 主 Sidebar 已以 `sidebarData.kernelSidebarTree` 作为主树来源
|
||
- `PrivateTree` 已改为直接消费 `page_tree` projection 可见行
|
||
- 对应文件:
|
||
- [sidebar.tsx](/mnt/Data1T/mnote/wolai-frontend/src/components/sidebar/sidebar.tsx)
|
||
- [private-tree.tsx](/mnt/Data1T/mnote/wolai-frontend/src/components/sidebar/private-tree.tsx)
|
||
|
||
### 3.3 文件树已收口为统一 projection consumer
|
||
|
||
- 文件树当前不再直接走嵌套 `SidebarTreeNode[]` 递归拼树
|
||
- 它已经建立在:
|
||
- `page_tree projection rows`
|
||
- `assetsByDoc`
|
||
- `buildVisibleRows(...)`
|
||
之上
|
||
- 对应文件:
|
||
- [rows.ts](/mnt/Data1T/mnote/wolai-frontend/src/lib/file-tree/rows.ts)
|
||
- [types.ts](/mnt/Data1T/mnote/wolai-frontend/src/lib/file-tree/types.ts)
|
||
- [file-tree.tsx](/mnt/Data1T/mnote/wolai-frontend/src/components/sidebar/file-tree.tsx)
|
||
|
||
### 3.4 picker 已退出旧拼树主路径
|
||
|
||
- `move-embed picker` 空查询态已不再读取 `documents[] -> buildDocumentTree(...)`
|
||
- 它现在直接消费 `kernelSidebarTree -> page_tree projection -> picker rows`
|
||
- 对应文件:
|
||
- [move-embed-picker-dialog.tsx](/mnt/Data1T/mnote/wolai-frontend/src/components/documents/move-embed-picker-dialog.tsx)
|
||
- [tree-projection.ts](/mnt/Data1T/mnote/wolai-frontend/src/lib/tree-projection.ts)
|
||
|
||
---
|
||
|
||
## 4. 本轮完成后的保留边界
|
||
|
||
### 4.1 旧拼树 helper 已退出主路径,但仍保留兼容边界
|
||
|
||
- [`buildDocumentTree(...)`](/mnt/Data1T/mnote/wolai-frontend/src/lib/documents.ts) 仍保留在兼容 helper 与旧单测里
|
||
- 但运行时主路径已不再由它构造 Sidebar / 页面树 / 文件树 / picker
|
||
|
||
### 4.2 文件树仍不是 Rust 直接输出的完整 file_tree projection
|
||
|
||
- 当前文件树已经消费统一 `page_tree projection`
|
||
- 但 `asset-folder` / `asset` / `index` 仍由前端 adapter 基于现有数据集补齐
|
||
|
||
### 4.3 Sidebar 壳仍然过重
|
||
|
||
当前 Sidebar 仍是超大客户端组件。
|
||
|
||
这不是 `Phase 4` 的阻塞项,但它解释了为什么下一个任务必须单列为独立 Rust Web tree shell 重构。
|
||
|
||
---
|
||
|
||
## 5. Phase 4 的重新定义
|
||
|
||
建议把 `Phase 4` 重新定义成下面这个最小目标:
|
||
|
||
> **统一树域 projection protocol,让 Sidebar 主树、页面树、文件树、move/embed picker 都只消费同一套 kernel projection family,并让旧拼树 helper 退出主路径。**
|
||
|
||
这版定义刻意不包含:
|
||
|
||
- 树域独立 Rust Web shell
|
||
- `Leptos`/`Dioxus` UI 重写
|
||
- Sidebar 整体壳替换
|
||
|
||
这些是 `Phase 4` 完成后的下一层任务。
|
||
|
||
---
|
||
|
||
## 6. Phase 4 拆分原则
|
||
|
||
### 原则 1
|
||
|
||
先冻结协议,再收 consumer。
|
||
|
||
### 原则 2
|
||
|
||
先收掉旧 helper 的主路径依赖,再谈树域 UI 重构。
|
||
|
||
### 原则 3
|
||
|
||
文件树不是第二套树,而是更宽对象范围的 projection。
|
||
|
||
### 原则 4
|
||
|
||
每一条树域 consumer 都必须能明确回答:
|
||
|
||
- 它消费的 projection 是什么
|
||
- 它本地状态只剩什么
|
||
- 它是否还在自己定义结构真相
|
||
|
||
---
|
||
|
||
## 7. Phase 4 任务拆分
|
||
|
||
建议把 `Phase 4` 拆成 6 个子任务。
|
||
|
||
---
|
||
|
||
## 8. P4-1:冻结树域 projection protocol
|
||
|
||
**状态:`DONE`**
|
||
|
||
**目标**
|
||
|
||
先把 Sidebar / 页面树 / 文件树要共同使用的 tree protocol 冻结下来。
|
||
|
||
**要做的事**
|
||
|
||
- 明确最小 tree item / tree row 字段
|
||
- 明确 `sidebar_tree`、`page_tree`、`file_tree` 的共用字段与差异字段
|
||
- 明确:
|
||
- `node_id`
|
||
- `parent_node_id`
|
||
- `node_type`
|
||
- `projection_kind`
|
||
- `depth`
|
||
- `position`
|
||
- `capabilities`
|
||
- `resource_meta`
|
||
- 明确哪些字段属于 projection
|
||
- 明确哪些字段只能留在 UI 本地状态
|
||
|
||
**交付物**
|
||
|
||
- [x] 树域 projection protocol 文档与类型:
|
||
- [tree-projection.ts](/mnt/Data1T/mnote/wolai-frontend/src/lib/tree-projection.ts)
|
||
- [x] 当前前端类型定义对齐方案
|
||
|
||
**完成判定**
|
||
|
||
- [x] 后续所有树域 consumer 都有统一协议可依赖
|
||
|
||
---
|
||
|
||
## 9. P4-2:统一 Sidebar 主树与页面树 consumer
|
||
|
||
**状态:`DONE`**
|
||
|
||
**目标**
|
||
|
||
让主 Sidebar、页面树相关视图都明确只消费 `kernelSidebarTree` / projection protocol。
|
||
|
||
**要做的事**
|
||
|
||
- 盘点 Sidebar 主树的所有树读取入口
|
||
- 清理仍然从 `documents[]` 直接拼主树的路径
|
||
- 把排序、层级、childCount、expand hint 统一收口到 projection
|
||
- 让主树 consumer 只保留:
|
||
- expanded
|
||
- selected
|
||
- hover
|
||
- DnD 中间态
|
||
|
||
**交付物**
|
||
|
||
- [x] Sidebar 主树消费边界收口
|
||
- [x] `PrivateTree` / 顶部树列表统一改读 `page_tree projection`
|
||
|
||
**完成判定**
|
||
|
||
- [x] 主 Sidebar 不再自己定义页面树结构
|
||
|
||
---
|
||
|
||
## 10. P4-3:把文件树收口为统一 projection consumer
|
||
|
||
**状态:`DONE`**
|
||
|
||
**目标**
|
||
|
||
让文件树从“前端继续拼装的树行系统”收口为统一 tree protocol 的 consumer。
|
||
|
||
**要做的事**
|
||
|
||
- 明确文件树和页面树的关系:
|
||
- 文件树 = 页面树骨架 + 更宽对象投影
|
||
- 把 `asset-folder` / `asset` / `index` 的协议层次化
|
||
- 收紧 `buildVisibleRows(...)` 的职责
|
||
- 它只负责 projection -> visible rows
|
||
- 不再负责定义结构真相
|
||
- 明确哪些对象后续应由 Rust projection 直接输出:
|
||
- `mindmap`
|
||
- `table`
|
||
- `asset`
|
||
- `book`
|
||
- `pdf`
|
||
|
||
**交付物**
|
||
|
||
- [x] 文件树 row model 收口方案
|
||
- [x] 文件树 projection consumer 边界
|
||
|
||
**完成判定**
|
||
|
||
- [x] 文件树不再被视为独立第二套树系统
|
||
|
||
---
|
||
|
||
## 11. P4-4:统一 move / embed picker 等兼容树域
|
||
|
||
**状态:`DONE`**
|
||
|
||
**目标**
|
||
|
||
把兼容树域 consumer 也切到 projection,结束双轨树模型。
|
||
|
||
**要做的事**
|
||
|
||
- 改成直接消费 projection tree / flat rows
|
||
- 搜索态和空查询态统一到同一目标对象口径
|
||
- 明确 picker 只消费 page tree,不再自带另一套树构造逻辑
|
||
|
||
**交付物**
|
||
|
||
- [x] picker 树域消费统一
|
||
|
||
**完成判定**
|
||
|
||
- [x] `buildDocumentTree(...)` 退出 picker 主路径
|
||
|
||
---
|
||
|
||
## 12. P4-5:收敛旧 helper 与兼容逻辑
|
||
|
||
**状态:`DONE`**
|
||
|
||
**目标**
|
||
|
||
让旧树 helper 不再占据主路径,只保留必要过渡边界。
|
||
|
||
**要做的事**
|
||
|
||
- 盘点 `buildDocumentTree(...)` 所有 consumer
|
||
- 区分:
|
||
- 主路径必须替换
|
||
- 过渡路径可暂留
|
||
- 收敛 `lib/documents.ts` 在树域中的责任
|
||
- 给保留的兼容 helper 标明过渡边界
|
||
|
||
**交付物**
|
||
|
||
- [x] 树域旧 helper 清单
|
||
- [x] 主路径替换完成
|
||
|
||
**完成判定**
|
||
|
||
- [x] 树域主路径不再依赖旧对象数组拼树
|
||
|
||
---
|
||
|
||
## 13. P4-6:Phase 4 验收矩阵与下一阶段交接
|
||
|
||
**状态:`DONE`**
|
||
|
||
**目标**
|
||
|
||
避免 `Phase 4` 再被提前写成“树域已重构完成”。
|
||
|
||
**要做的事**
|
||
|
||
- 建立 Phase 4 验收矩阵:
|
||
- Sidebar 主树 consumer
|
||
- 页面树 consumer
|
||
- 文件树 consumer
|
||
- picker consumer
|
||
- 旧 helper 退出主路径
|
||
- tree protocol 冻结
|
||
- 回写 checklist
|
||
- 明确 Phase 4 完成后才能进入:
|
||
- [sidebar-pagetree-filetree-rust-web-rebuild-v1.md](/mnt/Data1T/mnote/design/04-tree-domain/process/4-sidebar-pagetree-filetree-rust-web-rebuild-v1.md)
|
||
|
||
**交付物**
|
||
|
||
- [x] Phase 4 验收矩阵
|
||
- [x] 下一阶段交接说明
|
||
|
||
**完成判定**
|
||
|
||
- [x] 能明确回答“为什么现在可以做树域 Rust Web shell 重构”
|
||
|
||
### 验收矩阵
|
||
|
||
| 验收项 | 当前状态 | 说明 |
|
||
| --- | --- | --- |
|
||
| Sidebar 主树 consumer | `DONE` | 主 Sidebar 与 `PrivateTree` 已统一消费 `kernelSidebarTree -> page_tree projection` |
|
||
| 页面树 consumer | `DONE` | 顶部树列表、页面树扁平化视图不再各自 flatten 嵌套树 |
|
||
| 文件树 consumer | `DONE` | 文件树只消费 `page_tree projection + asset 映射`,`buildVisibleRows(...)` 只做 visible rows |
|
||
| picker consumer | `DONE` | `move-embed picker` 空查询态已改读 projection family |
|
||
| 旧 helper 退出主路径 | `DONE` | 运行时树域主路径不再调用 `buildDocumentTree(...)` |
|
||
| tree protocol 冻结 | `DONE` | `rowId/nodeId/parentNodeId/projectionKind/depth/position/capabilities/resourceMeta` 已固定 |
|
||
|
||
### 下一阶段交接
|
||
|
||
- 本阶段完成后,下一步唯一合理的大任务是:
|
||
- [sidebar-pagetree-filetree-rust-web-rebuild-v1.md](/mnt/Data1T/mnote/design/04-tree-domain/process/4-sidebar-pagetree-filetree-rust-web-rebuild-v1.md)
|
||
- 原因不是“树域 UI 已重写完成”,而是:
|
||
- 协议已经冻结
|
||
- consumer 已经统一
|
||
- 旧拼树 helper 已退出主路径
|
||
- 现在可以稳定做一次“换壳”,而不是边改协议边重写 UI
|
||
|
||
---
|
||
|
||
## 14. 建议执行顺序
|
||
|
||
建议顺序如下:
|
||
|
||
1. `P4-1` 冻结协议
|
||
2. `P4-2` 收主 Sidebar / 页面树 consumer
|
||
3. `P4-3` 收文件树 consumer
|
||
4. `P4-4` 收 picker / 兼容树域
|
||
5. `P4-5` 收旧 helper
|
||
6. `P4-6` 做验收矩阵和下一阶段交接
|
||
|
||
原因:
|
||
|
||
- 如果不先冻结协议,后面的 consumer 收口会一边做一边改字段
|
||
- 如果不先收主树和文件树,picker 再怎么改也只是边角修补
|
||
- 如果不收掉旧 helper,后面的 Rust Web tree shell 会继续背着双轨数据模型前进
|
||
|
||
---
|
||
|
||
## 15. 暂不纳入 Phase 4 的内容
|
||
|
||
下面这些先不要塞进 `Phase 4`:
|
||
|
||
- 用 `Leptos` / `Dioxus` 重写树域 UI
|
||
- 独立 Rust Web tree shell
|
||
- Sidebar 全量业务壳替换
|
||
- 搜索主面板迁移
|
||
- AI 主面板迁移
|
||
- Mindmap 主画布迁移
|
||
|
||
这些都属于 `Phase 4` 之后的阶段。
|
||
|
||
---
|
||
|
||
## 16. Phase 4 完成的最终标准
|
||
|
||
只有同时满足下面几条,才建议把 `Phase 4` 标成完成:
|
||
|
||
- Sidebar 主树、页面树、文件树、picker 都直接消费 kernel projection family
|
||
- `buildDocumentTree(...)` 不再处于树域主路径
|
||
- 文件树被正式定义为更宽对象投影,而不是第二套树
|
||
- tree protocol 已冻结
|
||
- React/Next 树域只保留渲染与局部交互状态,不再定义树结构真相
|
||
|
||
当前已经满足上述标准,因此 `Phase 4` 可以标记为完成;但这不意味着树域 Rust Web shell 已经完成。
|
||
|
||
---
|
||
|
||
## 17. 最终结论
|
||
|
||
`Phase 4` 当前最准确的职责是:
|
||
|
||
> **先把树域 consumer、协议、旧 helper 边界全部统一,确保树域真正只剩一个 truth 和一套 projection family。**
|
||
|
||
现在这一步已经完成,所以下一步的:
|
||
|
||
- Sidebar / 页面树 / 文件树 Rust Web tree shell 重构
|
||
|
||
才会变成一次稳定的“换壳”,而不是一次边重写协议边重写 UI 的高风险返工。
|