Files
mnote/ARCHITECTURE.md
T
lix-2026 f292c6710a feat: EditorRuntimeActor - 三层缓存/delta/事件架构
Phase A — EditorRuntimeActor 内存缓存层
- 新增 editor_actor.rs: EditorBlockDocument 内存态 + apply_command + load_or_init
- block.rs 四个写工具(replace/insert/delete/move)接入 actor 路径
- editor_actor feature flag(MNOTE_WEB_ENABLE_EDITOR_ACTOR=true 默认开启)
- bridge-runtime 三个核心函数公开化
- rust-toolchain: 1.89 → stable(修复 spike WASM 编译阻塞)

Phase B — 编辑器增量 delta channel
- BlockDelta/DeltaOperation 类型 + actor.build_block_delta()
- leptos-tiptap spike: mnote:editor:block-delta CustomEvent 监听 + JSON patch
- DocumentAiAgentPanel: 拦截 blockDelta → window dispatchEvent
- 工具响应含 blockDelta 字段供前端消费

Phase C — 事件 stream delta
- broadcast channel 在 AppState/actor/SSE 三层贯通
- tree_events SSE 端点发 block.delta 事件
- 旧客户端降级兼容

环境修复
- rustc recursion_limit = 1024(修复 Leptos SSR 类型深度溢出)
- run-convex-deploy.js(封装 Convex function 部署到本地后端 3210)

ref: design/07-ai/process/7-13-page-block-editor-runtime-actor-v1.md
2026-05-16 22:03:30 +08:00

309 lines
11 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# MNOTE 当前架构梳理
> 更新时间:2026-05-16
本文只描述当前仓库中真实成立的主线结构,以及当前最优先的架构收口点。
## 1. 当前主线结论
当前仓库的主线不是:
- `BlockNote-first`
- `Mindmap-first`
- “先拆掉 Convex 再谈 Rust”
当前主线固定为:
1. `tree-first graph kernel` 是长期对象真相层
2. `Convex` 继续保留为当前自托管存储 / 实时 / 文件协作底座
3. `mnote-web` 是当前 Rust Web 主执行面,负责 3000 gateway、server-first shell、query / command / projection / transport 与 realtime streamNext App Router 已降为 legacy compat / island bundle source,不再是当前主入口
4. 文档页默认主编辑器已切到页面内 `leptos-tiptap` island
5. `BlockNote` 已退出文档页默认主路径,仅作为历史参考实现 / 对照材料保留
一句话收口:
> **Rust 持有语义主导权,Convex 保留底座,前端逐步从重壳转向消费稳定 projection 与少量交互 island。**
补充口径:
> **主 Web 执行面当前以 `mnote-web` 为 3000 ownerNext App Router 只保留为 legacy compat、交互 island bundle source 与显式 debug/迁移辅助边界。**
## 2. 当前主线目录
- `/mnt/Data1T/mnote/wolai-frontend/`
当前 React island 与 legacy compat 代码来源;Next.js App Router 不再作为 3000 主入口,只在显式 legacy/debug 迁移边界继续服务重交互运行态与对照链。
- `/mnt/Data1T/mnote/rust/crates/core-protocol/`
Kernel 类型、projection 协议、编辑器协议、树 / 图核心术语。
- `/mnt/Data1T/mnote/rust/crates/bridge-runtime/`
Kernel query / command、bridge transport、Tiptap <-> editor document 适配、命令解释层。
- `/mnt/Data1T/mnote/rust/crates/mnote-web/`
Rust Web route、kernel projection、documents/search/mindmap shell、Hermes bridge、stream transport、compat,以及显式开启时的 debug shell;它是当前主 Web gateway / shell / transport owner。
- `/mnt/Data1T/mnote/wolai-frontend/convex/`
仍在使用的 Convex functions 与数据侧逻辑。
- `/mnt/Data1T/mnote/infra/convex/`
Convex 自托管部署与基础设施。
- `/mnt/Data1T/mnote/wolai-backend/`
辅助后端与异步处理,不是当前页面主链。
## 3. 当前页面运行结构
### 3.1 根布局与 legacy island source
- `/mnt/Data1T/mnote/wolai-frontend/src/app/layout.tsx`
职责:
- 作为 legacy Next / React island bundle source 的根布局
- 保留 Convex / Query Provider 等前端 island 运行时依赖
- 服务显式 legacy/debug/迁移边界
注意:
> **3000 当前根入口与文档页 shell 由 `mnote-web` 持有;Next App Router 不再是 3000 主入口或页面根布局事实源。**
### 3.2 工作区壳与 Sidebar
- `/mnt/Data1T/mnote/wolai-frontend/src/components/app-layout-shell.tsx`
- `/mnt/Data1T/mnote/wolai-frontend/src/hooks/use-sidebar-data.ts`
- `/mnt/Data1T/mnote/wolai-frontend/src/lib/tree-stream/use-sidebar-tree-stream.ts`
- `/mnt/Data1T/mnote/wolai-frontend/src/components/sidebar/use-preferred-sidebar-snapshot.ts`
当前 Sidebar 不是单一路径,而是三层组合:
1. 初始 SSR / route snapshot
2. query / refetch snapshot
3. tree stream live snapshot
`PreferredSidebarSnapshotProvider` 负责在 query 与 tree stream 之间做 freshness 选择,再把同一份 preferred snapshot 同时给:
- `Sidebar`
- `Breadcrumb`
- 文档页头标题消费链
这说明当前工作区树链已经进入正式收口阶段:`3000` 主壳已直接接入 `/api/tree/events` 的 snapshot / delta / resync consumer,并有浏览器 smoke 验证;但 preferred snapshot、page subtree、filetree 与补偿链还没有完全统一成唯一 live cache。
## 4. 文档页主链
### 4.1 入口
- `/mnt/Data1T/mnote/wolai-frontend/src/lib/documents/page-aggregate-loader.ts`
- `/mnt/Data1T/mnote/wolai-frontend/src/app/(app)/documents/[id]/page.tsx`
当前文档页读取主链已经不再由页面入口手工拼若干独立字段,而是:
1. 页面 SSR 入口通过 `page-aggregate-loader.ts` 直接请求 Rust `/api/page-aggregate/:id`
2. `DocumentContent` 的内容重试补拉也直接请求同一条 `/api/page-aggregate/:id` 正式读链
3. 读取主链不再回退到 TS builder;snapshot 不可用或不可信时直接显式失败
4. Next `/api/documents/page` 已退场为明确 `410` 的 compat 边界,不再参与文档页运行时主路径
对应聚合类型定义:
- `/mnt/Data1T/mnote/wolai-frontend/src/lib/documents/page-aggregate.ts`
### 4.2 文档壳
- `/mnt/Data1T/mnote/wolai-frontend/src/components/editor/document-shell.tsx`
- `/mnt/Data1T/mnote/wolai-frontend/src/components/editor/document-content.tsx`
`DocumentShell` 现在只是薄封装,文档页核心状态和交互壳集中在 `DocumentContent`
### 4.3 默认编辑器 host
- `/mnt/Data1T/mnote/wolai-frontend/src/components/editor/editor-host-config.ts`
- `/mnt/Data1T/mnote/wolai-frontend/src/components/editor/editor-host.tsx`
当前默认 host 为:
- `leptos_tiptap_island`
文档页主路径已不再暴露显式 debug host 选择;历史 `iframe_debug` 宿主仅剩源码参考,不再参与页面 host 选择面。
### 4.4 正式主编辑器
- `/mnt/Data1T/mnote/wolai-frontend/src/components/editor/leptos-tiptap-island-editor-host.tsx`
当前默认主编辑器已经是页面内 Leptos island,不再是 iframe bridge。
它负责:
- 加载 Leptos/WASM 编辑器本体
- 接收初始化内容与 page options
- 处理同页事件、命令、保存与状态同步
### 4.5 BlockNote 的当前位置
- `/mnt/Data1T/mnote/recycle/wolai-frontend/src/components/editor/blocknote-editor.tsx`
`BlockNote` 当前仍保留回收副本,但其定位已变成:
- 历史参考实现
- 对照材料 / 调试素材
而不是默认主编辑器方向。
## 5. 当前编辑器与页面聚合关系
当前文档页已经开始消费统一的前端侧 `PageAggregateProjection`,但仍不能说“页面域已完全统一成 Rust 单一真源”。
当前真实状态是:
- 读取主链已优先消费 Rust `mnote.page_aggregate.v1` snapshot
- Page Aggregate 已输出 `blockDocument``blockProjectionVersion``projectionSource`
- 标题链路已开始与工作区树 canonical snapshot 对齐
- 正文默认由 `leptos-tiptap` island 编辑与保存
- 页面设置已有一部分进入 island 运行时语义
- `page_tree` / `pageSubtree` 已进入统一聚合入口
- 页面/块 AI tools 已开始通过 Page Aggregate block projection 读取、定位、dry-run、替换、插入和受限移动块,并经 `page.body.save -> documents:updateContent` 持久化
但仍未完成的关键点是:
1. Rust 侧虽已提供最小 `Page Aggregate` snapshot 和 block projection v1,但当前 block projection 仍主要从 `documents.content` / local markdown content 投影,不是 EditorBlockDocument 原生落库完成态
2. 标题 / 正文 / 页面设置虽已开始收口到 `page.*` family,但 projection 回流与运行时语义仍未完全统一
3. AI 块工具最小闭环已启动,但 `scope=selection``format=page_xml/text`、多块插入、复杂块移动矩阵和持久审阅 UI 仍未完成
4. 客户端仍保留 preferred sidebar snapshot 与本地 aggregate state reducer,说明页面域单一真源仍在推进中
因此当前正确表述应是:
> **文档页读取主链已进入 Rust-first `page aggregate` 过渡态,但页面域单一真源仍未闭环。**
## 6. 当前树域结构
### 6.1 Kernel projection 与 route
- `/mnt/Data1T/mnote/rust/crates/mnote-web/src/routes/kernel.rs`
当前 Rust 已提供:
- `sidebar_tree`
- `page_tree`
- `file_tree`
- `subtree`
- `edges`
- `graph`
这些 route 说明树域 projection family 已经在 Rust 侧具备清晰边界。
### 6.2 树命令现状
- `/mnt/Data1T/mnote/wolai-frontend/src/lib/documents/tree-command-client.ts`
- `/mnt/Data1T/mnote/rust/crates/mnote-web/src/routes/tree.rs`
- `/mnt/Data1T/mnote/rust/crates/storage-convex-bridge/src/mapping.rs`
当前树命令已经开始以 `tree.*` 为 preferred command name,例如:
- `tree.node.create`
- `tree.node.rename`
- `tree.subtree.move`
但兼容层仍广泛保留:
- `documents.create`
- `documents.title.update`
- `documents.move`
这说明 tree command cutover 已开始,但还没有完成。
### 6.3 树 realtime 现状
当前 Sidebar 已有:
- query snapshot
- tree stream
- preferred snapshot 选择
正式的 snapshot + delta 主链已经固定到 `mnote-web``/api/tree/events`Next `/api/mnote-web/stream` 只保留 compat alias。
因此当前正确表述应是:
> **树域 realtime 主链由 Rust Web `/api/tree/events` 持有,前端只消费稳定 stream contract 与 projection。**
补充:
> **`3000` 主壳当前已不再通过 `/api/tree/projections/*` 额外维护第二条 runtime live fallbacksnapshot / delta / resync 直接消费 `/api/tree/events` 载荷。**
## 7. Mindmap 与 OnlyOffice
### 7.1 Mindmap
当前 Mindmap 不再是系统中心,而是:
- `tree-first graph kernel` 的一种视图 / 编辑挂件
它仍有:
- 文档内嵌块形态
- 独立页面形态
但不应再被理解为对象真相层。
### 7.2 OnlyOffice
OnlyOffice 仍然是:
- 独立页面型编辑器
它不直接嵌入正文主编辑画布;正文中通常通过附件块跳转进入。
## 8. 当前最优先的架构收口
当前最优先的三条主线,不是继续大规模 UI 重写,而是:
### 8.1 Page Aggregate
目标:
- 让标题 / 页面设置 / 正文 / page tree 统一成同一组 page aggregate projection 与 command family
对应设计稿:
- `/mnt/Data1T/mnote/design/05-editor-mainline/process/5-5-page-aggregate-single-truth-alignment-v1.md`
- `/mnt/Data1T/mnote/design/05-editor-mainline/process/5-6-page-aggregate-alignment-checklist-v1.md`
- `/mnt/Data1T/mnote/design/05-editor-mainline/done/5-5-1-page-aggregate-contract-v1.md`
### 8.2 Tree Command Cutover
目标:
-`tree.*` 成为正式命令面
- `documents.*` 降为兼容层
对应设计稿:
- `/mnt/Data1T/mnote/design/04-tree-domain/done/4-6-tree-command-protocol-cutover-stage2-v1.md`
### 8.3 Tree Realtime Event Stream
目标:
- 让 snapshot + delta 正式成为树域实时主链
- 减少当前 query/refetch/freshness 补偿链的长期存在
对应设计稿:
- `/mnt/Data1T/mnote/design/03-rust-web/process/3-3-rust-web-tree-realtime-event-stream-v1.md`
### 8.4 Page / Block AI Tooling
目标:
- 让 AI 读取、定位、dry-run 和精确块写入统一走 Rust Hermes tools、Page Aggregate block projection 与 `EditorCommand`
-`mnote.page.save` 固定为页面级兜底写入工具,不再代表长期精确块编辑主入口
- 补齐 `scope=selection``format=page_xml/text`、多块插入、复杂块移动矩阵和持久审阅 UI
对应设计稿:
- `/mnt/Data1T/mnote/design/07-ai/process/7-10-page-block-ai-tooling-execution-checklist-v1.md`
## 9. 当前不该再用的旧口径
下面这些说法现在都不准确:
- “默认文档页仍然是 `BlockNoteEditor`
- “主编辑器还没切到页面内 Leptos island”
- “当前最优先是继续证明 `leptos-tiptap` 能不能跑”
- “当前最优先是先做树域 UI 重构”
当前真正的卡点已经变成:
> **单一真源如何收口,以及 projection / command / realtime 三条链如何从兼容态进入正式主链。**