第 8 / 8 篇
整理于 · 9 分钟
九月重构修正了哪些边界
有限重构中的接口约定、页面状态和交易验证
贯穿项目的约定 本篇涉及 3 条
在初期部署与演示准备之后,代码中仍有需要处理的边界:部分接口直接返回数据库实体,复杂页面切换上下文时可能混入旧数据,而关闭弹窗并不意味着后端事务已经终止。
2026 年 9 月,项目围绕身份、前后端契约、复杂页面状态与数据库事务展开有限重构。它保留原技术栈,按限定入口修正行为并补充验证。
1. 有限重构的目标:沿用技术栈,修正接口与状态
本轮继续使用 Vue 3 + Element Plus + Pinia 和 Spring Boot 2.7 + MyBatis-Plus。
工作集中在四个方面:
- 接口契约:统一迁移入口的请求参数校验与读取响应 DTO;
- 状态机重构:重塑仪表盘、课程中心、订单页、课次详情四大复杂页面的交互生命周期;
- 消除竞争隐患:治理弹窗关闭与在途请求(In-Flight Requests)脱节引发的重复提交;
- 真实数据库事务验收:在隔离的真实 MySQL 环境下验证跨模块死锁防护与数据不变量。
2. 前后端契约:请求校验与读取响应
2.1 读取 DTO:明确返回字段与标识
在早期代码中,Controller 常常直接将数据库持久化实体(Entity)序列化为 JSON 返回给前端。这导致了严重的安全与概念混乱:
- 敏感字段泄露:部分用户信息接口曾无意中将密码哈希或内部凭据返回给前端;
- ID 概念混淆:前端难以分清返回的 ID 究竟是家长账号 ID(
userId)、绑定关系 ID(relationId),还是排课课次 ID(scheduleId)与课程开班 ID(courseInstanceId)。
迁移范围内的读取接口采用专用响应 DTO:
- 移除相关响应中的密码与内部凭据字段;
- 显式区分关系标识与用户主体标识;
- 对于数据暂缺状态(如学生未录入姓名),明确返回待核对提示状态,坚决不用虚假的默认字符串掩盖数据缺失。
2.2 请求与错误契约:规范 HTTP 语义
早期接口习惯用 HTTP 200 状态码包裹带有 code: 500 的业务异常。这种“伪成功”给前端拦截器与网络监控带来了极大困扰。
已迁移入口按以下 HTTP 语义处理错误:
- 400:请求字段格式不合法或缺失必填项;
- 403:跨权限或越权访问他人子女记录;
- 404:目标课程、课次或订单不存在;
- 409:状态冲突(如名额已被他人抢占、订单已超时、已存在相同绑定关系);
- 500:限定迁移路由中的未知服务端异常,对外返回固定提示,避免暴露原始异常细节。
3. 四大复杂页面的状态治理
3.1 仪表盘:各区域独立重试与图表生命周期
管理员与教师仪表盘包含多个异构数据卡片(营收统计、排课网格、AI 建议、出勤趋势)。
重构让相关卡片分别管理查询和错误状态,失败区域提供重试;同时在组件卸载时销毁 ECharts 实例。局部失败和图表清理有了对应处理,但这不等于所有网络异常或内存问题都已排除。
3.2 课程中心与订单页:单次筛选与上下文绑定
- 课程中心:筛选改为回车或点击按钮后显式提交;标签在内部维护为数组,在 API 边界序列化。这与输入后按时间延迟触发的防抖不同;
- 订单页:每张订单卡片独立维护自己的操作上下文,支付弹窗中的待付金额与倒计时严格绑定当前选中的单据,防止在多订单切换时串改支付金额。
3.3 课次详情:可操作性的可读状态
对于调课、请假与评价按钮,系统显示不可操作的原因,例如课次未结束或不满足请假规则,让禁用状态有可读解释。
4. 关键交互隐患修复:在途请求锁与弹窗解耦
本轮处理的一类交互问题,是把在途提交状态错误地绑定到弹窗可见性。风险过程如下:
- 用户在付款弹窗中点击“确认支付”,前端加锁并向后端发送扣款请求;
- 用户在等待网络响应的过程中关闭了弹窗;
- 旧系统缺陷:前端在弹窗关闭回调中顺手将“提交锁”释放了,但此时后端的扣款请求依然在路上;
- 用户重新打开弹窗后再次提交,就可能发出重复支付请求。请求重复不等于已发生两次实际扣款,后端仍需检查状态。
9 月重构把相关动作的在途提交状态从弹窗状态中分离:
- 请求未结束时,关闭弹窗不清除该动作的提交保护;
- 重新打开相关弹窗时,按钮根据在途状态限制再次提交;
- 页面或业务对象变化后,响应处理会核对原请求上下文,避免旧数据和提示写入新的上下文。
这些是对应页面和动作的保护,并不是覆盖全系统的业务锁,也不能代替后端事务校验。
5. 本轮验证的范围与结果
9 月事务验证在独立隔离的 MySQL 9.3 中使用原有表结构和合成数据。记录包括:
- 跨模块事务:28 个指定场景和 22 项双连接检查通过,覆盖相关锁等待、竞争与回滚;
- 数据不变量:12 项断言检查测试状态下的余额、名额与流水关系;
- 四角色 API 流程:169 项 API 断言通过,使用的是测试角色与合成数据。
验证留下的边界
这些数字属于指定测试批次,存在覆盖重叠,不能相加成全系统验收数量。记录还保留以下边界:
- 契约迁移未覆盖全系统:成绩模块的非法孩子查询仍可能返回旧的
HTTP 200 / code: 500;历史报名同秒歧义继续拒绝处理,订单缺少学员姓名时显示待核对。 - 依赖检查尚未全部闭合:自动依赖门禁仍为待完成,人工检查仅确认限定范围内对齐。
- 验证范围有限:未迁移模块、既有业务库兼容、真实第三方支付和全站移动端未纳入本轮验收;验证码与第三方支付仍有模拟能力。
- 展示状态:体验环境已清理,在线展示安排已取消。180 个图位是清单,不代表截图已采集,也不是当前在线服务的证据。
本轮能确认的是:限定入口的接口、状态和交易规则经过修订,并留下了对应验证。继续接入或展示时,应沿用这些范围说明,不能把有限重构完成扩写为全系统已经通过生产验收。