Commit Graph
7 Commits
Author SHA1 Message Date
wangzhibiaoandCursor b7a9b89ec5 完善考勤:支持未签到学员人工登记缺勤
名册中无任何打卡记录的已报到学员此前只能"先签到再改成缺勤",会留下伪造的签到事实。

- 新增 POST /train/attendance/mark-absence,权限 train:attendance:edit,带操作日志
- 写入 attendance_status=0、sign_in_time 与 sign_out_time 保持 NULL、manual_flag=1,
  缺勤原因必填,绝不伪造签到时间
- 前置条件全部 fail closed:课次已开始、与课次同属一个开班计划、
  参训状态必须恰好为已报到;请假不得被自动改写为缺勤
- 已有考勤记录时拒绝新建并引导改用调整考勤记录,
  并发命中唯一索引转为同一业务错误,不泄露数据库异常
- 名册新增 canMarkAbsence,前端直接采用后端判定,登记后可继续调整考勤记录
- 未改动出勤率统计口径与 Analytics 业务策略

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-09-22 17:04:41 +08:00
wangzhibiaoandCursor b7eab13a83 修复权限:首页按真实业务身份选择工作台
菜单层与 API 层已按真实业务身份限制,但首页只看 role_key,导致有 train_teacher
角色却无教师档案绑定的账号先进入教师工作台再被 API 拒绝。

- 身份服务新增 hasActiveTeacherIdentity / hasActiveStudentIdentity,
  语义与原菜单过滤完全一致,异常吞掉返回 false
- SysLoginController 抽出 resolveSelfServiceIdentity 作为唯一事实源,
  自服务菜单过滤与 getInfo 新增的 selfService 标志共用该方法,不新增第三套规则
- 前端 store 新增 selfService 标志,缺失时默认全 false 并严格布尔化,登出时重置
- 自服务路由过滤与首页渲染改为按身份标志判断,且与角色授权取交集,与菜单层口径一致
- 有角色无业务档案的账号落到普通首页,Dashboard 组件根本不创建,
  不会发起任何自服务 API 请求,页面给出明确的未绑定提示

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-09-22 17:04:26 +08:00
wangzhibiaoandCursor aeb76ce35a 修复住宿:统一住宿生命周期状态与状态变更入口
住宿状态在数据库与业务上只有 0 预分配 / 1 已入住 / 2 已退宿三种,不存在 3 已调房。
调房是业务操作,真实语义为旧记录置退宿、新记录置在住,不应表现为独立状态值。

- 前端住宿页面移除筛选项与两处状态标签中的"已调房"(status=3),补齐历史表格缺失的预分配标签
- 后端通用 PUT /train/accommodation 封死 accommodation_status 写入路径,
  状态变更只能经办理入住、办理退宿、调房等专属业务操作
- 新增住宿状态白名单守卫,非法整数与新增即退宿一律拒绝入库

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-09-22 17:03:43 +08:00
wangzhibiao ecfd38be17 修复权限:隔离教师工作台与学员中心菜单自服务可见性 2026-09-22 11:59:38 +08:00
wangzhibiao 08b8abe778 测试考勤:覆盖参训状态签到守卫与真实前端策略 2026-09-22 00:05:56 +08:00
wangzhibiao 38d4851a18 测试考勤:覆盖首次签到与未签到展示 2026-09-21 23:21:35 +08:00
wangzhibiao 481c998e82 测试门禁:覆盖失败提示与空响应重发保护 2026-09-21 16:56:06 +08:00