2026-05-04-03-21-40 增加前后端协同和NIfTI导出

This commit is contained in:
2026-05-04 03:29:54 +08:00
parent a6f3836460
commit a9b6d2d76a
15 changed files with 1040 additions and 67 deletions

View File

@@ -0,0 +1,105 @@
# 实现方案
时间戳2026-05-04-03-21-40
## 修改目标
将当前前端静态演示升级为前后端协调系统:
- 后端统一管理登录状态、用户列表、项目列表和演示环境。
- 项目列表默认载入 `Head_CT_DICOM``Head_CT_ReConstruct`
- 恢复演示环境出厂设置后恢复默认项目和默认用户。
- 逆向工作区通过后端生成并下载 `.nii.gz` 分割 mask。
- 继续部署到 `http://192.168.3.11:4000/`
## 涉及路径
- `WebSite/package.json`
- `WebSite/server.ts`
- `WebSite/src/lib/api.ts`
- `WebSite/src/types.ts`
- `WebSite/src/App.tsx`
- `WebSite/src/components/Login.tsx`
- `WebSite/src/components/Overview.tsx`
- `WebSite/src/components/ProjectLibrary.tsx`
- `WebSite/src/components/ReverseWorkspace.tsx`
- `WebSite/src/components/UserManagement.tsx`
- `WebSite/data/state.json`
- `WebSite/exports/`
- `.gitignore`
- `工程分析/测试方案-2026-05-04-03-21-40.md`
- `工程分析/经验记录.md`
## 技术路线
1. 新增 Express 后端 `server.ts`
- 开发环境通过 Vite 中间件服务前端。
- API 和页面共用 `4000` 端口,避免跨域和前后端端口不一致。
2. 后端状态持久化。
- 使用 `WebSite/data/state.json` 保存演示状态。
- 默认用户包括 `admin / 123456`
- 当前登录状态由后端统一维护,所有浏览器轮询 `/api/session` 同步。
3. 默认项目载入。
- 后端扫描 `../Head_CT_DICOM``.dcm` 数量。
- 后端扫描 `../Head_CT_ReConstruct``.stl` 文件列表。
- 构造默认项目 `head-ct-demo`,包含 DICOM/STL 路径、数量、模块名称。
4. 恢复演示环境出厂设置。
- `POST /api/demo/reset` 重建默认用户、默认项目、登录状态。
- 前端系统管理页点击按钮后调用该接口,并刷新用户和项目相关数据。
5. 前端 API 化。
- `Login` 调用 `/api/login`
- `App` 调用 `/api/session` 并轮询同步登录状态。
- `Overview` 调用 `/api/overview`
- `ProjectLibrary` 调用 `/api/projects`
- `UserManagement` 调用 `/api/users``/api/demo/reset`
- `ReverseWorkspace` 调用 `/api/projects/:id``/api/projects/:id/export-mask`
6. NIfTI 导出。
- 后端生成 NIfTI-1 单文件 `.nii.gz`
- 使用 Node `zlib.gzipSync` 压缩。
- 文件保存到 `WebSite/exports/`,同时以 attachment 下载。
- NIfTI 内容先采用演示 mask 体素数据,尺寸、标签信息和项目元数据由后端生成。
7. 部署。
- `npm run build`
- `npm run lint`
- 使用 `tmux` 运行 `npm run serve -- --host 0.0.0.0 --port 4000`
## 数据流
登录:
前端登录页 -> `POST /api/login` -> 后端验证账号密码 -> 更新共享 session -> 所有浏览器轮询 `/api/session` 后同步状态。
项目:
前端项目库 -> `GET /api/projects` -> 后端扫描或读取默认项目状态 -> 展示 DICOM 数量、STL 模块、路径和状态。
重置:
系统管理页 -> `POST /api/demo/reset` -> 后端重建默认状态 -> 前端刷新用户和项目。
导出:
逆向工作区 -> `POST /api/projects/:id/export-mask` -> 后端生成 `.nii.gz` -> 前端下载。
## 兼容性与回滚方案
- 保留 Vite/React 前端结构,后端通过同端口中间件接入。
- DICOM/STL 仍不进入 Git。
- `WebSite/data/state.json``WebSite/exports/` 作为运行态文件默认不纳入提交。
- 若后端服务异常,可回滚 `server.ts` 和前端 API 调用改动,恢复纯前端 Vite 部署。
## 预计文件变更
- 新增 `WebSite/server.ts`
- 新增 `WebSite/src/lib/api.ts`
- 修改 `WebSite/package.json`
- 修改 `WebSite/src/types.ts`
- 修改主要页面组件以接入 API。
- 修改 `.gitignore` 排除运行态数据和导出文件。
- 更新工程分析文档和经验记录。
## 人工审核状态
本次用户明确要求需求分析、实现方案、测试方案、执行修改均不用人工二次确认。
状态:自动确认,继续执行。

View File

@@ -0,0 +1,132 @@
# 测试方案
时间戳2026-05-04-03-21-40
## 测试目标
验证系统已经从纯前端静态演示升级为前后端协调系统并确认登录同步、默认项目、恢复出厂设置、NIfTI 导出和部署均可用。
## 静态检查
- 检查 `server.ts` 是否提供 API 和前端页面服务。
- 检查 `src/lib/api.ts` 是否统一封装 API 请求。
- 检查项目列表、系统管理、逆向工作区是否不再依赖硬编码假数据。
- 检查 `.gitignore` 是否排除 `WebSite/data/``WebSite/exports/`、DICOM、STL、依赖和构建产物。
## 构建与类型检查
`WebSite/` 下执行:
```bash
npm run lint
npm run build
```
预期结果:
- TypeScript 类型检查通过。
- Vite 构建通过。
## API 验证
启动后端服务后验证:
```bash
curl -s http://127.0.0.1:4000/api/health
curl -s http://127.0.0.1:4000/api/session
curl -s http://127.0.0.1:4000/api/projects
curl -s http://127.0.0.1:4000/api/users
curl -s -X POST http://127.0.0.1:4000/api/demo/reset
```
预期结果:
- health 返回 `ok`
- projects 包含默认项目 `head-ct-demo`
- 默认项目 `dicomCount``300`
- 默认项目 STL 模块包含 `Head_CT_ReConstruct` 下的 `.stl` 文件。
- reset 后默认项目仍存在。
## 登录同步验证
- 浏览器 A 登录 `admin / 123456`
- 浏览器 B 刷新或等待轮询后读取到已登录状态。
- 浏览器 A 或 B 登出后,另一个浏览器轮询后同步到未登录状态。
命令级验证:
```bash
curl -s -X POST http://127.0.0.1:4000/api/login -H 'Content-Type: application/json' -d '{"account":"admin","password":"123456"}'
curl -s http://127.0.0.1:4000/api/session
curl -s -X POST http://127.0.0.1:4000/api/logout
curl -s http://127.0.0.1:4000/api/session
```
## NIfTI 导出验证
执行:
```bash
curl -L -o /tmp/revoxelseg-mask.nii.gz -X POST http://127.0.0.1:4000/api/projects/head-ct-demo/export-mask
file /tmp/revoxelseg-mask.nii.gz
gzip -t /tmp/revoxelseg-mask.nii.gz
```
预期结果:
- 下载文件存在。
- 文件为 gzip 压缩数据。
- `gzip -t` 校验通过。
- 响应文件名后缀为 `.nii.gz`
## 页面验证
- 打开 `http://192.168.3.11:4000/`
- 登录页可正常登录。
- 总体概况显示后端统计数据。
- 项目库默认显示头部 CT 演示项目。
- 项目详情展示 `Head_CT_DICOM``Head_CT_ReConstruct` 相关信息。
- 系统管理页点击“恢复演示环境出厂设置”后,项目仍恢复为默认 DICOM/STL。
- 逆向工作区可导出 `nii.gz` mask。
## 回归风险
- 引入后端后部署方式从纯 Vite 改为 Express + Vite 中间件,需要确认 `4000` 服务由 `server.ts` 托管。
- 后端共享登录状态是演示同步方案,不等同生产级多用户 session。
- NIfTI 文件当前为演示 mask非医学级真实 STL 体素化结果。
## 人工审核状态
本次用户明确要求无需人工二次确认。
状态:自动确认,继续执行。
## 执行结果
- `npm run lint` 执行成功。
- `npm run build` 执行成功。
- Vite 仍有大 chunk 警告,当前不影响本次功能。
- 已新增 Express 后端 `server.ts`,并通过 `npm run serve -- --host 0.0.0.0 --port 4000` 托管前后端。
- `GET /api/health` 返回 `ok: true`
- `GET /api/projects` 返回默认项目 `head-ct-demo`
- 默认项目载入结果:
- `dicomCount: 300`
- `modelCount: 9`
- `dicomPath: Head_CT_DICOM`
- `modelPath: Head_CT_ReConstruct`
- `POST /api/demo/reset` 执行成功,重置后默认项目仍载入 `Head_CT_DICOM``Head_CT_ReConstruct`
- `POST /api/login` 使用 `admin / 123456` 登录成功。
- `GET /api/session` 登录后返回 `authenticated: true`
- `POST /api/logout` 登出成功。
- `GET /api/session` 登出后返回 `authenticated: false`
- `POST /api/projects/head-ct-demo/export-mask?format=nii.gz` 执行成功。
- `/tmp/revoxelseg-mask.nii.gz` 通过 `gzip -t` 校验。
- 解压后 NIfTI magic 为 `n+1\0`
- `POST /api/projects/head-ct-demo/export-mask?format=nii` 执行成功,生成未压缩 `.nii`
- `http://192.168.3.11:4000/` 返回 `HTTP/1.1 200 OK`
- 当前部署由 `tmux` 会话 `revoxelseg-dicom` 托管。
## 剩余说明
- 当前导出的 NIfTI mask 是可下载、格式有效的演示分割体数据。
- 真实医学级 STL 反向体素化仍需后续加入 DICOM 空间解析、STL 坐标配准、网格体素填充和标签体系。

View File

@@ -109,3 +109,75 @@ C. 解决问题方案
D. 后续如何避免问题
每次调整部署端口前先检查端口占用和现有 `tmux` 会话;部署后同时验证 `127.0.0.1` 与目标内网 IP并把实际访问地址写入测试方案执行结果。
## 2026-05-04-03-21-40 从纯前端演示升级为前后端协调系统
A. 具体问题
原系统登录、项目列表、用户列表、出厂重置和导出都是前端静态假数据,不同浏览器之间无法共享状态。
B. 产生问题原因
项目初始形态是 Vite/React 前端演示,没有后端 API、共享状态存储和统一部署入口。
C. 解决问题方案
新增 Express 后端 `server.ts`,用同一 `4000` 端口服务 API 和前端页面。后端通过 `WebSite/data/state.json` 维护演示状态,前端通过 `/api/session` 轮询同步登录状态,并将项目、用户、概况、重置和导出功能全部接入 API。
D. 后续如何避免问题
新增跨浏览器共享功能时,默认先判断状态是否必须由后端维护;涉及多浏览器一致性的功能不要放在组件静态数组或浏览器本地状态中。
## 2026-05-04-03-21-40 默认医学数据项目载入
A. 具体问题
项目列表需要默认载入 `Head_CT_DICOM``Head_CT_ReConstruct`,恢复演示环境出厂设置后也必须恢复这两个默认数据目录。
B. 产生问题原因
旧项目列表使用硬编码医疗项目示例,和当前仓库中的 DICOM/STL 数据资产没有建立关系。
C. 解决问题方案
后端启动和读取状态时扫描 `Head_CT_DICOM``.dcm` 数量与 `Head_CT_ReConstruct``.stl` 文件列表,生成默认项目 `head-ct-demo``POST /api/demo/reset` 使用同一逻辑重建默认项目。
D. 后续如何避免问题
演示数据入口统一放在后端默认项目构建函数中,避免多个页面分别硬编码 DICOM/STL 路径或数量。
## 2026-05-04-03-21-40 NIfTI 导出闭环
A. 具体问题
逆向工作区需要最终生成 `nii``nii.gz` 格式的分割 mask而旧界面只有导出按钮没有后端文件生成能力。
B. 产生问题原因
项目尚未实现真实 STL 到 DICOM 空间的体素化算法,也没有文件导出 API。
C. 解决问题方案
新增 `POST /api/projects/:projectId/export-mask`,后端生成 NIfTI-1 单文件 mask并按请求输出 `.nii``.nii.gz``.nii.gz` 使用 Node `zlib.gzipSync` 压缩,并通过 `Content-Disposition` 触发下载。
D. 后续如何避免问题
导出类功能需要先定义后端接口、文件格式和校验命令。后续实现真实体素化时,可替换当前演示 mask 生成函数,但保留 API 和下载流程。
## 2026-05-04-03-21-40 Vite 中间件 HMR 端口冲突
A. 具体问题
Express + Vite 中间件启动时,默认 HMR WebSocket 端口 `24678` 被其他服务占用,日志出现端口冲突。
B. 产生问题原因
同一机器同时运行多个 Vite 服务,默认 HMR 端口可能重复。
C. 解决问题方案
`createViteServer` 中指定 `server.hmr.port = 24679`,使本项目后端服务使用独立 HMR 端口。
D. 后续如何避免问题
多项目并行部署时,除了业务端口外,也检查 Vite HMR 端口;发现冲突时为每个项目分配独立 HMR 端口。

View File

@@ -0,0 +1,68 @@
# 需求分析
时间戳2026-05-04-03-21-40
## 原始需求摘要
用户要求严格使用代码编纂工作流处理本次项目修改,并在最开始确认工作流整体流程;但本次需求分析、实现方案、测试方案和执行修改均不需要人工二次确认。
功能需求:
- 完善整个代码,使网页变为前后端协调系统。
- 不同浏览器的登录信息能够同步。
- 完善网页基本功能。
- 项目列表默认载入 `Head_CT_DICOM``Head_CT_ReConstruct`
- 选择“恢复演示环境出厂设置”后,也重新载入默认的 `Head_CT_DICOM``Head_CT_ReConstruct`
- 最终生成的分割 mask 为 `nii``nii.gz` 格式。
## 业务目标
- 从纯前端静态演示升级为带后端 API 的协同系统。
- 将登录状态、用户列表、项目列表、演示环境状态统一由后端维护,避免不同浏览器各自持有不一致的假数据。
- 以本地默认医学数据目录为演示项目来源,前端项目库默认展示真实目录统计。
- 在逆向工作区提供后端生成 `nii.gz` 分割 mask 的下载能力,形成完整演示闭环。
## 输入与输出
输入:
- `Head_CT_DICOM/`:默认 DICOM 序列目录。
- `Head_CT_ReConstruct/`:默认 STL 重建模型目录。
- 登录账号信息,默认管理员 `admin / 123456`
输出:
- 后端 API。
- 前端通过 API 读取和更新登录、用户、项目、导出状态。
- 项目库默认项目:头部 CT DICOM 与重建 STL 演示项目。
- 恢复出厂设置后恢复默认用户和默认项目。
- 逆向工作区导出 `.nii.gz` 分割 mask。
## 影响范围
- `WebSite/package.json`
- `WebSite/server.ts`
- `WebSite/src/App.tsx`
- `WebSite/src/types.ts`
- `WebSite/src/lib/api.ts`
- `WebSite/src/components/Login.tsx`
- `WebSite/src/components/Overview.tsx`
- `WebSite/src/components/ProjectLibrary.tsx`
- `WebSite/src/components/ReverseWorkspace.tsx`
- `WebSite/src/components/UserManagement.tsx`
- `WebSite/data/` 运行态数据目录
- `WebSite/exports/` 生成导出目录
- `工程分析/经验记录.md`
## 风险点
- 当前需求的“前后端协调系统”范围较大,本次优先完成可运行的后端 API、共享状态和演示导出闭环不实现生产级认证权限。
- “不同浏览器登录信息同步”在生产系统通常应基于用户独立 session。本演示系统为满足同步需求会用后端统一维护当前登录状态并通过前端轮询同步。
- 真实 STL 到 DICOM 空间的精确逆向体素化需要医学影像空间信息、STL 坐标配准和体素填充算法。本次先生成符合 NIfTI-1 格式的演示分割 mask并保留后续替换真实体素化算法的接口。
- `4000` 端口当前为前端 Vite 服务;引入后端后需要改为 Express + Vite 中间件统一服务。
- DICOM/STL 原始数据仍不应提交到 Git。
## 待确认问题
- 本次用户已明确免二次人工确认,因此无需等待确认。
- 后续如需真实医学级逆向体素化,需要进一步确认 DICOM 空间坐标、STL 单位、配准矩阵和目标输出标签体系。