Files
mnote/design/old/08-legacy-rust-kernel/process/document-access-performance-root-cure-v1.md

460 lines
12 KiB
Markdown
Raw Permalink 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.
# [recycle] 文档访问性能根治重构路线 v1
> 更新时间:2026-04-16
>
> 相关文档:
> - `/mnt/Data1T/mnote/ARCHITECTURE.md`
> - `/mnt/Data1T/mnote/design/old/08-legacy-rust-kernel/process/ai-frontend-simplification-plan-v1.md`
> - `/mnt/Data1T/mnote/design/old/08-legacy-rust-kernel/done/rust-kernel-cutover-v1.md`
## 1. 目标
这份文档只回答一个长期问题:
> **如果不满足于“临时优化”,而要从架构上根治文档访问和页面切换卡顿,mnote 应该重构成什么样。**
本文的目标不是“再做几处按需加载”,而是定义:
- 哪些前端能力应继续保留
- 哪些能力应退出当前重前端壳
- Rust Web 层应该采用什么形态
- `BlockNote` 应该如何被隔离,而不是继续拖慢整个页面系统
---
## 2. 当前事实
结合当前仓库结构,可以先确认四个事实:
### 2.1 当前最重的前端成本,不在服务端语言
当前文档页主链仍然是:
`documents/[id]/page.tsx -> DocumentShell -> DocumentContent -> BlockNoteEditor`
而且存在以下典型问题:
- 文档进入页面后仍有 `meta -> content -> editor` 的串行加载链
- `DocumentShell``DocumentContent` 仍在客户端串联挂载
- `BlockNoteEditor` 本身是当前最重的前端运行时之一
- 文档页周边仍挂载多类抽屉、面板和桥接组件
这说明当前访问速度问题的核心,不是“Node 不够快”,而是:
> **页面切换时仍然把太多东西当成同一层前端运行时来初始化。**
### 2.2 当前只有一类能力明确难以短期替换
从产品结构看,短期最难替换的是:
- `BlockNote`
因为它同时承担:
- 文档编辑核心
- 自定义 block 运行时
- 当前正文交互和保存链
而下面这些东西,从长期看都不是必须继续绑在当前 React/Next 大壳里的:
- Sidebar / 页面树 / 文件树
- 搜索壳与搜索结果面板
- Mindmap
- AI 面板
- 历史 / 评论 / 回链 / 页面选项等周边面板
- 在线表格
### 2.3 OnlyOffice 不应被当成主阻塞项
根据当前架构,OnlyOffice 本来就是独立页面型编辑器,不是正文内嵌主编辑器。
这意味着:
- 它不会决定文档页的首屏切换模式
- 它可以继续保留“外挂页面/外部编辑器”定位
- 它不应影响主文档访问性能路线判断
### 2.4 Mindmap 是优先级更高的可替换对象
当前 Mindmap 虽然复用了前端组件链,但它并不像 BlockNote 那样不可轻易动。
因此长期上:
- Mindmap 可以先于 BlockNote 重写
- 它很适合作为“从当前重前端壳中剥离”的第一批对象
---
## 3. 根治原则
如果目标是“根治”,而不是“补丁式提速”,那么应遵守以下原则。
### 3.1 页面切换必须先回到“读优先”
当前问题的根子之一,是页面切换几乎默认在进入“编辑器世界”。
长期正确方向应改为:
- 先快速进入页面阅读态
- 再按需进入编辑态
- `BlockNote` 不得阻塞普通页面访问
换句话说:
> **文档页要从“先挂编辑器,再展示页面”改成“先展示页面,再按需挂编辑器”。**
### 3.2 除 `BlockNote` 外,其余能力应尽量退出当前重前端壳
长期目标不应是“继续给当前 Next/React 应用做瘦身”,而应是:
- 让能退出的都退出
- 让必须保留在浏览器的只剩真正需要浏览器的那部分
理想形态是:
- 文档阅读页:极薄
- 文档编辑岛:`BlockNote`
- 外挂编辑器:OnlyOffice
- 独立能力:Mindmap、AI、搜索、Sidebar 等各自最小化
### 3.3 Rust 化的意义在于“统一业务执行面”,不是“自动更快”
把东西改成 Rust 并不会自动让页面切换更快。
Rust 真正的价值在于:
- 统一业务执行平面
- 让文档、块、导图、搜索、树结构、审计、AI 业务桥收口到同一体系
- 支持更薄的前端和更强的 SSR / server-first 输出
所以“Rust 化”必须和“页面运行模型重构”一起发生,才构成根治。
---
## 4. 技术选型判断
这一节只回答一个问题:
> **长期重构时,到底是“就用 Rust”,还是要明确选择 `axum` 等 Rust Web 框架。**
结论先给出:
> **不能只说“用 Rust”。长期要落地,必须明确分层选型。推荐方案是:`axum` 作为 Web/服务承载层,配合 `Leptos Islands` 作为 server-first 页面壳;不推荐只用 `axum`,也不建议把 Dioxus/Yew 作为主文档访问层的第一选择。**
### 4.1 为什么不能只说“Rust”
“Rust”是语言,不是 Web 渲染方案。
如果只决定“以后改成 Rust”,但不明确:
- 服务端路由由谁承接
- 页面 SSR 由谁承接
- islands / hydration 模型由谁承接
- 浏览器交互层由谁承接
那最后很容易回到:
- 只是把 API 改写成 Rust
- 但前端页面模型仍然没变
这不能根治。
### 4.2 `axum` 的定位:非常适合做 Web 承载层,但不负责前端 UI 模型
官方 `axum` 文档显示,它非常适合承担:
- Router
- Handler
- Middleware
- JSON / Query / Form / WebSocket / SSE
- `tokio` 上的高并发服务
这使它非常适合作为 mnote 长期的:
- API 层
- 文档查询层
- 树结构聚合层
- 搜索层
- AI / Hermes 业务桥
- SSR 页面外壳承载层
但要注意:
> **`axum` 不是前端渲染框架。它能承接 Web 服务,不会替你解决“页面如何减少 hydration、如何隔离 BlockNote”这类前端模型问题。**
因此,**只用 `axum` 不够。**
### 4.3 为什么推荐 `Leptos Islands`
官方 Leptos Islands 文档最值得关注的点是:
- 默认服务端组件不进入客户端
- 只有显式 `#[island]` 的部分才被编译到浏览器
- islands 应尽量“小而具体”
这和 mnote 的长期目标高度一致,因为你现在最想要的是:
- 绝大多数页面内容不再变成大块客户端运行时
- 只有真正需要交互的部分进入浏览器
- `BlockNote` 成为最后一个重交互 island
也就是说,Leptos Islands 的思路天然支持:
- 页面树/文件树作为轻交互 island
- 搜索框作为轻交互 island
- AI 面板作为独立 island
- `BlockNote` 作为最后的重 island
- 其余大量阅读内容只做 server-rendered HTML
这比“继续在全页 React hydration 里做局部优化”更接近根治。
### 4.4 为什么不把 Dioxus 作为主推荐
官方 Dioxus Fullstack 文档自己就把它定位得更偏“app-like”:
- 它支持 SSR
- 但更强调交互型应用
- 文档中明确区分 CSR 的 app 架构与 SSR 的 site 架构
而 mnote 的长期目标不是继续维持一个“整页 app 先跑起来”的文档访问模型,而是:
- 页面先出来
- 交互再局部接上
所以 Dioxus 不是不能用,而是**不如 Leptos Islands 对这个目标直接。**
### 4.5 为什么不把 Yew 作为主推荐
Yew 更接近经典 Rust/WASM 前端框架。
它的问题不是能力不够,而是:
- 更偏客户端应用思路
- 不天然突出 islands-first
- 对你当前“尽量减少客户端代码、把交互压缩为少数岛”的目标,不是最优选
---
## 5. 推荐的长期方案
## 5.1 总体选型
推荐长期架构采用:
- **服务承载层:`axum`**
- **页面壳与 islands 模型:`Leptos Islands`**
- **业务执行面:现有 mnote Rust `core-protocol + bridge-runtime + storage-convex-bridge` 继续演进**
- **AI runtimeHermes API Server**
- **最后保留的重编辑岛:`BlockNote`**
一句话版:
> **`axum` 负责服务,`Leptos` 负责薄页面与 islandsRust 内核负责业务,Hermes 负责 agent`BlockNote` 留作最后的重前端孤岛。**
## 5.2 为什么这是最适合 mnote 的方案
因为这个方案同时满足四个条件:
### A. 适合逐步迁移
你不需要一次性推翻所有前端。
可以先把:
- Sidebar
- 页面树 / 文件树
- 搜索壳
- 阅读页
- Mindmap
逐步迁到 `axum + Leptos`
再把 `BlockNote` 留在最后处理。
### B. 适合“读写分离”
`Leptos Islands` 很适合把页面拆成:
- 读页面:服务端输出
- 写页面:局部 island
这正是文档访问性能根治的核心。
### C. 适合 Rust 单栈长期收口
当前你已经做过大范围 Rust 重构,未来继续统一到:
- Web 壳
- 业务协议
- AI 业务桥
- CLI
会比继续维护“Rust 内核 + 重 Next 前端壳”的分裂状态更稳定。
### D. 风险可控
你不需要一开始就重写 `BlockNote`
最难的部分可以留到最后,不会卡死整个长期路线。
---
## 6. 最终目标架构
长期目标建议收敛成下面这张逻辑图:
```text
浏览器
-> axum 路由层
-> Leptos server-rendered 文档壳
-> 少量 islands
- Sidebar / 页面树 / 文件树
- Search
- AI 面板
- Mindmap(重写后)
- BlockNote(最后保留的重岛)
axum / Leptos
-> mnote Rust 业务执行面
- 文档
- 块
- 搜索
- 导图
- 审计 / trace / event
Hermes API Server
-> 调用 mnote Rust 暴露的业务能力桥
OnlyOffice
-> 继续独立页面 / 外挂编辑器
```
在这个目标架构里:
- 页面切换不再默认进入“整页前端应用”
- 绝大多数阅读内容不需要大块 hydration
- `BlockNote` 成为唯一需要谨慎处理的大前端负担
---
## 7. 推荐迁移顺序
长期路线建议分四阶段,不建议一口气重做。
## Phase 1:先把文档访问模型改成 server-first
先做:
- 用 Rust Web 壳承接文档阅读态
- 页面进入时直接输出 `meta + content`
- 不再进入页面后再串行拉正文
- 把“页面切换”和“编辑器启动”拆开
这一阶段的目标不是替换 BlockNote,而是先把它从切页主链里移走。
## Phase 2:优先重写可替换的常驻模块
优先级建议:
1. Sidebar / 页面树 / 文件树
2. 搜索壳与搜索结果页
3. 页面选项、历史、评论、回链等周边面板
4. AI 面板
原因:
- 这些东西是跨页面常驻能力
- 高频出现
- 比 BlockNote 更容易先抽离
## Phase 3:重写 Mindmap,继续缩小前端重负担
Mindmap 是非常适合优先退出当前重前端壳的对象。
建议:
- 把导图数据和执行面继续放在 Rust
- 前端重新实现为更轻的独立渲染层
- 不再依赖当前文档页大壳去承载
## Phase 4:最后再处理 BlockNote
这时再决定:
- 是否继续保留 BlockNote,但隔离为独立 island
- 是否逐步替换 BlockNote 的部分能力
- 是否长期把编辑体验拆成更多 Rust 原生能力 + 少量 JS 编辑器兼容层
**在此之前,不建议把 BlockNote 当成第一刀。**
---
## 8. 非目标
为了避免路线漂移,下面这些都不应被误认为“根治方案”。
### 8.1 不是“把 Next API 改成 Rust 就算完成”
如果页面仍然是:
- 重客户端壳
- 重 hydration
- 切页即初始化编辑器
那只是服务端换语言,不是根治。
### 8.2 不是“先全面重写 BlockNote”
BlockNote 是最难对象,不应先作为第一刀。
正确顺序应是:
- 先移除外围负担
- 最后再碰 BlockNote
### 8.3 不是“继续在当前 React 壳里无限做局部修补”
按需加载、拆组件这些短期仍有价值,但如果最终仍然保留:
- 大型客户端文档壳
- 大型常驻 Sidebar
- 大型客户端页面切换模型
那还是治标不治本。
---
## 9. 最终建议
如果以“根治文档访问性能”为唯一目标,我给出的长期技术判断是:
> **应该继续推进 Rust 主导重构,但不是笼统地说“以后用 Rust”,而是明确采用 `axum + Leptos Islands + mnote Rust 内核 + Hermes` 的组合。**
其中:
- `axum`
适合做 Web 服务承载层、API、SSE、AI 业务桥、SSR 外壳。
- `Leptos Islands`
适合做 server-first 文档页和极小交互岛,是把 `BlockNote` 隔离成“最后一个重前端岛”的最佳路线。
- `Dioxus`
可以关注,但更适合作为偏 app 化交互场景的备选,不是当前文档访问性能根治的第一推荐。
- `Yew`
不作为当前主路线推荐。
最后用一句话收口:
> **mnote 的根治路线,不是“把现有前端改快一点”,而是“把除了 BlockNote 之外的大多数页面能力从当前重前端壳中迁出,交给 Rust 主导的 server-first Web 架构承载”。**
---
## 10. 外部参考
以下外部资料支持上面的技术判断:
- `axum` 官方文档:
https://docs.rs/axum/latest/axum/
- Leptos Islands 指南:
https://book.leptos.dev/islands.html
- Dioxus Fullstack SSR 文档:
https://dioxuslabs.com/learn/0.7/essentials/fullstack/ssr/