已完成用户APP首期功能开发

交付用户端首期页面、配套接口、后台资源及测试文档。用户APP构建、静态分析和三个管理后台构建通过;完整测试仍有2项失败,后端模型注释检查未通过,详见交付记录。
This commit is contained in:
czl231
2026-09-13 00:57:32 +08:00
parent a0a4bb1218
commit 3ef33b531d
793 changed files with 40959 additions and 1204 deletions

View File

@@ -0,0 +1,45 @@
# 用户端 App 报修照片日志
操作时间2026-09-07。操作类型扩展。影响模块用户App、Client照片接口、受控文件存储、既有工单证据表。
## 操作前后
现场照片原为未开放按钮,现支持相册/相机来源选择、1—3张照片、预览、删除、去重、上传和工单关联。客户端要求至少一张旧API客户端仍可省略photos。每张JPG/PNG不超过2MiB服务端再次验证扩展名、MIME、完整解码和4096像素边界。
上传使用独立账户与内容摘要目录不复用头像目录或权限。完整临时文件写入后原子移动相同内容重复上传复用URI。工单与reported照片证据在同一事务中越权或无效照片导致整张工单回滚。客户端缓存上传结果提交失败重试不重复上传成功照片。
详情批量查询证据只返回UUID、添加时间、来源和完整性标记。读取同时验证用户、工单归属和证据关联返回private/no-store及nosniff并记录访问日志。页面支持读取失败重试与放大预览。
## 代码变更
| 文件 | 关键函数与位置 |
| --- | --- |
| backend/api/internal/logic/upload/ticket_photo.go | 新增存储UploadTicketPhoto第43行、ServeTicketPhoto第95行摘要路径和账户归属 |
| backend/api/internal/logic/client/user/ticket_photo.go | saveTicketPhotos第34行事务关联TicketPhoto第74行双重授权ticketPhotosForList批量元数据 |
| backend/api/internal/logic/client/user/address_ticket.go | 创建可选photos及事务列表照片元数据 |
| backend/api/internal/routers/client.go、client_test.go | POST ticket-photos、GET tickets/:identity/photos/:photoIdentity与路由测试 |
| apps/user_app/lib/ui/features/tickets/repair_photos.dart | 第27行RepairPhotos选择、删除、预览RepairPhoto缓存上传URI |
| apps/user_app/lib/ui/features/tickets/repair_page.dart | 图片必填、上传期间保护、重试复用、确认摘要 |
| apps/user_app/lib/ui/features/tickets/ticket_photos.dart、ticket_detail_page.dart | 第8行TicketPhotos鉴权缩略图、重试、预览和添加时间 |
| apps/user_app/lib/data/services/api_client.dart | 第153行uploadImage共用鉴权保持旧头像方法和错误提示兼容 |
| apps/user_app/lib/data/repositories/client_repository.dart、domain/models/service_ticket.dart | 上传/读取照片、submitRepair可选photos、安全解析元数据 |
| backend/api/internal/logic/upload/ticket_photo_test.go、client/user/ticket_photo_test.go | 格式、大小、尺寸、路径、归属、事务回滚与读取缓存测试 |
| apps/user_app/test/ui/repair_page_test.dart | 选图注入失败重试UUID相同且上传次数为1 |
没有新增数据库字段或表、迁移、种子或本机数据库/缓存。复用cs_ticket_evidence文件沿用API工作目录runtime/uploads可用HEQI_UPLOAD_DIR指定受控存储不能公开映射该目录。
## 验证结果
- Go全包测试、vet、API构建通过格式伪造、2MiB限制、4096像素边界、目录穿越、头像URI误用、跨账户/工单读取、关联失败整体回滚均有测试。
- Flutter58项测试通过analyze无问题05/42的16组宽度/文本缩放截图通过Web release构建通过。旧头像提示回归发现后已保持兼容。
- contract:sync和contract:check通过48个资源新路由纳入测试。
- 浏览器从系统文件选择器选取64×64蓝白验收图案描述注明验收无需派单选择临时完整地址后确认提交自动进入详情照片能重新读取并放大。
- 工单TK1788794635076747500UUID为01a07c78-0344-7b67-acba-b3e3f289974d。随后浏览器确认取消已取消且按钮消失证据保留。
- 鉴权GET=200、image/png、Cache-Control含no-store/private匿名GET=401。读取图片与原验收图尺寸相同64×64全部像素差异为0SHA256不同不能声称原文件字节保真。
- 临时地址01a07c74-5c76-7805-873a-4d82b8c48977已归档列表恢复仅原默认地址。没有修改原地址、原工单或其他账户。浏览器error/warn为空。
## 剩余范围与维护
来源user_camera/user_gallery完整性capture_time_unknowncaptured_at暂存客户端添加时间只以added_at输出。页面明确提示拍摄时间/位置未核实,不伪造现场取证。原始拍摄时间、真实定位、原生相机验收、语音、持久化草稿、补充照片、工作人员查看用户照片的完整入口、联系工程师与改期仍待完成。
当前10图部分实现、48图尚无完整对应页面、0图严格全功能1:1通过。远程数据库保存证据记录不代表多实例共享文件存储已部署后续迁移必须保留资源归属与受保护读取。