- Workbench 独立页(/admin/workbench,adminOnly 守卫,全屏布局,MUI 风格) - 工具栏:历史栈/刷新/地址栏/搜索/添加/密码库/侧栏折叠/返回 - 侧边栏:分组+固定区+折叠+拖拽调宽+打开方式(内嵌/新标签/弹窗) - PanelFrame:懒加载/保留切换/LRU(3)/15s 超时失败回退/proxy 模式 - VaultDrawer:PIN 解锁/搜索/详情复制/锁定(复用 passwords API) - 后台顶栏「工作台」入口 + 路由注册;localStorage 持久化
84 lines
5.7 KiB
Markdown
84 lines
5.7 KiB
Markdown
# 工作台模块项目计划(tools/workbench)
|
||
|
||
> 独立完整项目流程:调研 ✓ → 设计规范 ✓ → 本计划 → 实现 → 审查 → 验证。
|
||
> 布局调研:lib-1(VSCode 四层 / Dashy Workspace / Vivaldi Web Panels / Arc pinned / Homepage groups + iframe 技术建议)。
|
||
> 设计规范:frontend-pack/design skill(8px 网格、语义色 token、层次/留白/焦点环/深浅色/加载空错误态)。
|
||
|
||
## 1. 模块定位
|
||
|
||
「面板工作台」:浏览器式多面板聚合界面(左侧侧边栏 + 顶部工具栏 + 右侧 iframe 内容区),叠加密码库快捷取用。仅管理员(adminOnly)可进入。
|
||
|
||
## 2. 技术方案
|
||
|
||
| 项 | 决定 |
|
||
|---|---|
|
||
| 风格 | **MUI**(与后台一致,MD3 主题复用 frontend/src/admin/theme.js) |
|
||
| 路由 | 独立页面 `/workbench`(React Router,挂管理后台路由树外或独立 BrowserRouter 区——用后台同一入口 admin 应用内加路由最简,basename /admin 下 `/admin/workbench`?——**决定:独立入口**(admin.html 已有),路由挂 `/admin/workbench`,与 Dashboard 等并列,顶栏入口按钮跳转;整页全屏布局不带 AdminLayout 侧栏(工作台自带侧边栏) |
|
||
| 代码位置 | `frontend/src/tools/workbench/`(独立工具区,页面+组件+密码库组件+工具函数全在这,方便后续升级) |
|
||
| 鉴权 | 入口守卫:无 token → 跳 /login.html;非 admin → 403 提示返回(复用后台守卫模式) |
|
||
| 数据 | admin_links API(复用 frontend/src/api/adminLinks.js)+ passwords API(复用) |
|
||
| proxy | `/api/proxy/fetch?url=&token=`(iframe query token,复用 Embed.jsx 的 needsProxy 逻辑) |
|
||
|
||
## 3. 文件结构
|
||
|
||
```
|
||
frontend/src/tools/workbench/
|
||
├── Workbench.jsx # 页面入口(路由挂载点 + 鉴权守卫 + 布局组装)
|
||
├── components/
|
||
│ ├── Toolbar.jsx # 顶部工具栏(◀▶↻ 地址栏 搜索 添加 密码库 侧栏开关 返回)
|
||
│ ├── Sidebar.jsx # 左侧边栏(固定区 + 分组列表 + 折叠 + 拖拽调宽可选)
|
||
│ ├── PanelFrame.jsx # iframe 内容区(加载态/超时/失败回退/LRU 保留)
|
||
│ ├── AddPanelDialog.jsx # 添加面板弹窗(URL/命名/分组/图标 + 打开方式)
|
||
│ └── VaultDrawer.jsx # 密码库抽屉(PIN 解锁/搜索/复制,MUI)
|
||
├── hooks/
|
||
│ ├── usePanels.js # 面板数据/打开集合/历史栈/持久化(localStorage)
|
||
│ └── useVault.js # 密码库解锁状态/条目加载(复用 passwords API)
|
||
└── index.js # 模块导出(便于未来升级替换)
|
||
```
|
||
|
||
## 4. 功能清单
|
||
|
||
### 核心(必须)
|
||
- [ ] 鉴权守卫(adminOnly)
|
||
- [ ] 工具栏:◀ 后退 / ▶ 前进(当前面板历史栈)、↻ 刷新、只读地址栏、🔍 搜索(面板名/URL/分组)、+添加、🔑 密码库、侧边栏折叠、返回前台
|
||
- [ ] 侧边栏:admin_links 按 category 分组 + 固定区(pin),点击切换,当前项左侧 2px primary 指示条 + surface-container 底(MUI 化:ListItemButton selected 态)
|
||
- [ ] iframe 区:懒加载(首次激活创建)、display:none 切换保留状态、**超时+load 双保险加载态**、失败(超时/空白启发式)显示「在新标签打开」回退按钮
|
||
- [ ] 打开方式:内嵌(默认)/ 新标签(target=_blank)/ 弹窗(modal)——面板项右键或添加时选择,存面板设置
|
||
- [ ] 添加面板弹窗:URL + 标题 + 分组 + 图标(favicon 预览)+ 打开方式;保存到 admin_links(复用现有 API)
|
||
- [ ] localStorage 持久化:打开面板集合、当前面板、历史栈、侧边栏折叠态
|
||
- [ ] 密码库抽屉:PIN 解锁(复用 /api/passwords/unlock,服务端会话互通)→ 条目列表(标题/用户名)+ 搜索 + 详情(密码明文)+ 一键复制(clipboard);未设 PIN 引导去 /passwords.html;只读取用不编辑
|
||
- [ ] 空态/加载态/错误态:无面板引导添加、加载骨架、加载失败重试
|
||
|
||
### 进阶(尽力)
|
||
- [ ] LRU iframe 保留(最多 3 个活跃,超出销毁最久未用,记录 URL 重建)
|
||
- [ ] 每面板定时刷新(可选 30s/5min/30min)
|
||
- [ ] 侧边栏拖拽调宽 + 记忆
|
||
- [ ] 分组折叠状态持久化
|
||
|
||
## 5. 设计规范(design skill + 调研要点)
|
||
|
||
- 8px 网格间距;一屏内不超过 2 种圆角(MUI 默认 8px/20px pill)
|
||
- 语义色 token(MD3):工具栏/侧边栏 surface-container、选中 primary-container、hover surface-variant
|
||
- 选中态:左侧 2px primary 指示条(VSCode 模式)或 MUI selected 态,二选一统一
|
||
- 深色模式默认适配(后台已有 data-theme 机制)
|
||
- 焦点环(focus-visible)、语义 HTML(nav/main/aside/button)、触控目标 ≥40px
|
||
- 加载态用骨架/居中 spinner;空态带图标+CTA;错误态带重试
|
||
- iframe title 属性必须;allow 权限策略按面板
|
||
- 工具栏高度 48-56px、侧边栏默认 240px(可 180-360 拖拽)
|
||
|
||
## 6. 实施与质量流程
|
||
|
||
1. 派 designer 按本计划实现(一个会话,MUI + 复用后台主题/api)
|
||
2. ora 审查(鉴权/安全/iframe 处理/状态管理/无障碍)→ 修复
|
||
3. 验证:npm run build + 后台入口跳转 + admin 权限拦截 + 面板切换/proxy/密码库全链路冒烟
|
||
4. commit + 用户验收
|
||
|
||
## 7. 验收标准
|
||
|
||
- [ ] 非 admin 无法进入(无 token 跳登录、非 admin 403)
|
||
- [ ] 面板分组/固定/切换/关闭/添加/持久化全部可用
|
||
- [ ] proxy 面板正常嵌入;X-Frame-Options 拒绝的面板有回退提示
|
||
- [ ] 密码库解锁→搜索→复制链路通(与服务端会话互通)
|
||
- [ ] 深浅色、320/768/1440 三档响应式正常
|
||
- [ ] build 通过、无 console 错误
|