test(api): 更新API客户端契约测试以符合YAML规范
- 更新登录响应模拟数据以匹配真实的AppLoginVo结构 - 添加认证客户端租户和授权字段验证 - 增加操作码枚举验证测试用例 - 移除对旧token别名的兼容性测试 - 修复测试用例中的短信验证码长度一致性问题 - 更新区域接口路径为PC专用路径 - 调整分片上传接口参数以符合新契约定义 refactor(api): 重构API客户端实现以严格遵循YAML契约 - 添加认证操作码和短信操作码枚举验证 - 实现严格的token响应解析只接受access_token字段 - 使用pickDefined函数过滤请求体中未定义的字段 - 重构认证接口参数映射以符合契约定义 - 更新区域接口路径为PC专用路径/genealogy/pc/region/* - 优化分片上传接口参数结构与契约保持一致 - 添加操作码枚举验证函数toRequiredOperationCode - 实现请求体字段选择性提取功能 feat(auth): 优化认证页面的验证码处理流程 - 添加takeCaptchaToken函数用于一次性获取验证码票据 - 更新短信验证码长度验证从4-6位改为精确4位 - 在登录和密码重置流程中集成验证码票据处理 - 修复验证码发送后票据清理逻辑 - 更新HTML模板中的验证码输入字段属性 chore(config): 提取常量配置并扩展配置对象结构 - 将客户端ID、租户ID和令牌键提取为常量 - 扩展配置对象返回客户端配置信息 - 更新配置测试用例以验证新增配置项 docs(planning): 更新PC接口对接规划文档 - 更新契约源说明以反映YAML冻结契约 - 添加YAML与在线Apifox复核对比内容 - 更新阻断项状态表格 - 修订登录响应token字段处理规范 - 更新文件上传和行政区划接口规范说明 style(profile): 优化相册管理页面的文件上传交互 - 将封面和照片OSS ID输入改为隐藏字段 - 添加文件选择标签以改善用户体验 - 移除手动输入OSS ID的选项保持界面简洁
This commit is contained in:
+53
-7
@@ -74,7 +74,9 @@
|
||||
4. 当前仓库代码;
|
||||
5. 旧规划和历史交接记录。
|
||||
|
||||
Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一业务契约 owner。`utils/ApiClient.js` 是前端路径和请求方法的唯一 owner。页面脚本只能调用 `ApiClient` 业务方法,不能直接拼 URL 或调用 Axios。
|
||||
通常以 Apifox 的 PC 目录作为 PC 前端接口的正式契约源。2026-07-28 用户明确指定本轮直接以 `D:/WorkSpace/Java/Genealogy/doc/apifox/genealogy-pc-openapi.yaml` 对接,因此该 YAML 是本轮冻结契约;在线 Apifox 的旧重复记录不再覆盖它。`utils/ApiClient.js` 是前端路径和请求方法的唯一 owner。页面脚本只能调用 `ApiClient` 业务方法,不能直接拼 URL 或调用 Axios。
|
||||
|
||||
旧 OpenAPI 文件不再作为新增功能依据,只用于结构化差异比较和追踪导出遗漏。
|
||||
|
||||
如果 Apifox 在线内容发生变化,先更新本地 OpenAPI、本规划的受影响章节和契约测试,再修改运行时代码。不得让文档、测试和运行时同时保留两套契约。
|
||||
|
||||
@@ -117,6 +119,24 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
4. 当前 96 个操作全部被声明为需要 `Authorization`,连注册、登录、短信发送和验证中心也不例外。这与未登录流程冲突,必须在 Apifox 逐项修正 security。
|
||||
5. 当前有 21 个成功响应使用无业务属性的 `ObjectResult`,12 个使用无元素 Schema 的 `ListResult`;另有 `LineagePersonTreeView` 名义上是专用 DTO,但没有任何属性。
|
||||
|
||||
### 4.3 2026-07-28 补齐版 YAML 与在线 Apifox 复核
|
||||
|
||||
补齐文件 `genealogy-pc-openapi.yaml` 含 98 个 path、137 个 HTTP operation、17 个 tag、319 个 schema;旧 `PC.openapi.json` 含 71 个 path、96 个 operation、68 个 schema。补齐文件新增了家谱、成员、相册、文章、祭祀、通知、反馈、VIP 和官网内容等路径及 DTO,但它还不能替代在线 Apifox:
|
||||
|
||||
1. 已实际登录并打开 Apifox“家谱”项目的 PC 模块。在线概览显示 **142 个接口、87 个数据模型**,与补齐 YAML 的 137 个 HTTP operation 不一致。
|
||||
2. 在线“认证登录”目录仍显示 **12 个接口**,同时存在:
|
||||
- 错误旧路径:`genealogy/pc/auth/sms/{operationCode}/code`
|
||||
- 正确路径:`/genealogy/pc/auth/sms/{operationCode}/code`
|
||||
|
||||
补齐 YAML 只包含正确路径,因此 C02 在线尚未完成。
|
||||
3. 补齐 YAML 给注册、密码登录、短信登录和短信发送标了 `security: []`;在线密码登录详情仍展示必需的 `Authorization` API Key,并显示 `Auth 1`。因此 C03 的导出定义和在线详情冲突。
|
||||
4. 在线 `GET /genealogy/pc/auth/profile` 成功响应仍为泛型 `ObjectResult`;展开后的 `data` 只有任意附加属性,没有 `ProfileView` 字段。补齐 YAML 同样引用泛型 `ObjectResult`,C04/C06 未完成。
|
||||
5. `ProfileUpdateBody.avatar` 仍为 `integer<int64>`,而 `FileUploadVo.ossId`、`LineagePersonView.avatarOssId` 等 OSS ID 为 `string`;部分头像字段也仍为 `integer<int64>`。C10 未完成。
|
||||
6. 已用真实登录响应和后端 `AppLoginVo` 复核:token 的唯一 JSON 字段是 `access_token`;原 YAML 的 `token`、`accessToken`、`tokenValue`、`userId`、`tenantId`、`clientId` 均不是该响应的直接字段,现已删除。
|
||||
7. `ProfileUpdateBody` 仍只有 `nickName`、`realName`、`avatar`、`sex`、`birthday`、`email`,没有地区字段,也没有说明缺省、`null`、空串的清空语义。C07/C18 未完成。
|
||||
|
||||
用户已明确要求本轮直接按补齐 YAML 施工,所以在线旧短信路径和公开接口 security 残留不再阻断本轮实现。YAML 自身仍存在的 profile 泛型响应、头像 ID 类型冲突和更新清空语义缺失继续保留为阻断项,前端不得自行补造。
|
||||
|
||||
## 5. 实施前必须解决的契约阻断项
|
||||
|
||||
以下事项不是前端自由选择,必须先在 Apifox 明确:
|
||||
@@ -144,6 +164,20 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
| C19 | 多数 View 没有 `canEdit` / `canDelete` 等权限字段 | 页面无法可靠决定按钮可见性 | 增加能力字段,或提供明确且可实现的角色规则 |
|
||||
| C20 | 文章、相册、祭祀只有删除操作 | 没有真实 ID 来源和完整资源流程 | 补全 PC 列表/详情/新增/修改后才开放页面 |
|
||||
|
||||
当前复核状态:
|
||||
|
||||
| 阻断项 | 状态 | 在线/补齐文件证据 |
|
||||
| --- | --- | --- |
|
||||
| C02 | 本轮按 YAML 解决 | 只实现带 `/` 的正确路径,不保留旧路径 fallback |
|
||||
| C03 | 本轮按 YAML 解决 | 验证、注册、登录、短信、找回使用 `security: []`;其他认证接口携带 Bearer |
|
||||
| C04/C06 | 阻断 | profile GET 在线及 YAML 都只有泛型 `ObjectResult` |
|
||||
| C07 | 阻断 | `ProfileUpdateBody` 没有地区字段 |
|
||||
| C01/C08 | 前端按后端 PC 实链解决 | 只调用 `/genealogy/pc/region/*`;列表按 `RegionSelectVo` 的 `regionCode/regionName/regionLevel` 读取,不保留公共路径 fallback |
|
||||
| C09 | 前端按后端 PC 实链解决 | `SysOssResumableInitVo` 明确提供 `uploadId/instant/ossId/url/fileName/uploadedChunks`,完成响应使用 `SysOssUploadVo` |
|
||||
| C10 | 前端边界解决 | 后端初始化 `ossId` 为 Long、完成响应为 string;浏览器统一转十进制字符串,隐藏回填且不转 `Number` |
|
||||
| C13 | 后续日期模块仍阻断 | 本阶段上传与区划响应不消费日期;其他模块仍需逐字段核验 Java 日期类型 |
|
||||
| C18 | 阻断 | 未说明可选更新字段的省略、`null`、空串语义 |
|
||||
|
||||
阶段 0 验收标准:
|
||||
|
||||
- Apifox 中不存在旧短信路径和双区划路径;
|
||||
@@ -246,8 +280,18 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
| `passed` | R/A | 决定校验成功或失败 |
|
||||
| `validToken` | I | 一次性票据,不显示、不落长期存储 |
|
||||
| `message` | R | 安全地显示验证结果 |
|
||||
| 登录响应的 `token` / `accessToken` / `tokenValue` | I | Apifox 收口为一个正式字段后保存 |
|
||||
| `userId`、`tenantId`、`clientId`、`clientKey` | I/R | 会话上下文或诊断信息,不作为用户编辑字段 |
|
||||
| `access_token` | string / I | 登录接口 `data`;密码或短信登录成功时立即保存,后续仅用于 Bearer 鉴权 |
|
||||
| `expire_in` | integer<int64> / I/R | 登录接口 `data`;登录成功时取得,可用于会话到期提示,不由用户填写 |
|
||||
| `client_id`、`clientKey`、`deviceType`、`userType` | string / I/R | 登录接口 `data`;登录成功时取得,仅作会话上下文或诊断,不回传为用户输入 |
|
||||
| `profile` | object / R | 登录接口 `data.profile`;登录成功后取得,可用于页面只读展示或资料页初始回填 |
|
||||
| `profile.userId`、`profile.tenantId`、`profile.userNo` | integer/string、string、string / I/R | 后端自动产生;不得让用户手工填写,业务 ID 超出 JS 安全整数时保持字符串 |
|
||||
| `profile.phone`、`profile.nickName`、`profile.realName`、`profile.email` | string/null / R | 后端用户资料;登录成功后只读展示或作为资料页回填,编辑时仍只提交 `ProfileUpdateBody` 允许字段 |
|
||||
| `profile.avatar` | integer/string/null / R | 后端头像 OSS ID;只读回填,用户换头像必须经文件选择和上传组件产生,禁止手填 OSS ID |
|
||||
| `profile.sex` | enum `0/1/2` / R | 后端用户资料;页面映射男/女/未知 |
|
||||
| `profile.birthday` | date/null / R | 后端用户资料;页面按日期展示 |
|
||||
| `profile.registerSource`、`profile.loginIp`、`profile.loginDate` | string/null / R/I | 后端自动产生;只读或内部诊断,不作为表单输入 |
|
||||
| `profile.status` | string / R/I | 后端账号状态;只读或内部诊断,不作为表单输入 |
|
||||
| `profile.clientKey`、`profile.deviceType` | string / I/R | 后端登录上下文;只读或内部诊断 |
|
||||
|
||||
#### 认证业务流程
|
||||
|
||||
@@ -258,7 +302,7 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
3. 若 `required=false`,直接提交密码登录。
|
||||
4. 若需要验证,调用 challenge,展示服务端指定控件,再调用 verify。
|
||||
5. 得到 `validToken` 后与 MD5 密码一起登录。
|
||||
6. 成功后仅保存一个正式 token 字段;Apifox 必须选定 `token`、`accessToken` 或 `tokenValue` 的唯一字段,不能长期兼容三个别名。
|
||||
6. 成功后只读取并保存 `data.access_token`;`token`、`accessToken`、`tokenValue` 均视为非法旧响应,不做兼容读取。
|
||||
|
||||
短信类动作:
|
||||
|
||||
@@ -284,6 +328,7 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
现有页面整改点:
|
||||
|
||||
- 当前 `avatarOssId` 字段名与请求契约 `avatar` 不一致;
|
||||
- 补齐 YAML 中 `avatar` 仍是 `integer<int64>`,但示例值已超过 JavaScript 安全整数范围;浏览器边界必须按十进制字符串保留精度,且只能由上传响应自动回填,不能转 `Number` 或让用户手填;
|
||||
- 缺少 `realName`、`email` 和性别“未知”;
|
||||
- 页面现居地区、父亲、微信/QQ、学历/职业不在 `ProfileUpdateBody`,不得混入保存请求;
|
||||
- 在后端增加地区字段前,“保存地区”按钮必须关闭或改成纯查询演示;
|
||||
@@ -312,7 +357,8 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
- `FileUploadVo.ossId`:I,隐藏写入业务表单;
|
||||
- `url`、`thumbnailUrl`:R,用于预览;
|
||||
- `fileName`、`originalName`:R,用于文件列表;
|
||||
- 初始化的 `instant`、已上传分片和秒传 OSS 信息尚未定义,C09 完成前不得猜测;
|
||||
- 初始化 `instant=true` 时直接读取 `ossId/url/fileName` 完成秒传;`instant=false` 时使用服务端 `uploadId` 与 `uploadedChunks` 跳过已上传分片;
|
||||
- 初始化 Long `ossId` 和完成响应 string `ossId` 均在浏览器边界转为十进制字符串;
|
||||
- 上传成功但业务保存失败时,当前契约没有释放引用接口,必须让后端补充生命周期规则。
|
||||
|
||||
统一由 `public/js/upload-pages.js` 管理分片、进度、重试、取消、MD5 和隐藏 ID。各业务页面不得复制上传算法,也不得出现“请输入 OSS ID”的可见输入框。
|
||||
@@ -339,7 +385,7 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
|
||||
### 7.5 行政区划
|
||||
|
||||
先完成 C01,只实现选中的唯一一套路径。
|
||||
本 PC 前端只实现 `/genealogy/pc/region/*`,不调用重复的 `/genealogy/region/*`,也不保留 fallback。
|
||||
|
||||
| 字段 | 必填性 | 类型 | 页面处理 |
|
||||
| --- | --- | --- | --- |
|
||||
@@ -350,7 +396,7 @@ Apifox 是 method、path、参数、DTO、枚举、权限和错误码的唯一
|
||||
| `limit` | 可选 query | A | 搜索组件固定合理上限,不让用户自由输入 |
|
||||
| `clientid` | 可选 header | A | 统一请求层注入 |
|
||||
|
||||
在 `RegionView` 补齐前不能假设响应一定含 `regionCode`、`regionName`、`regionLevel`。个人资料当前也没有可保存的地区字段,因此区划组件只能在有真实消费字段的页面启用提交。
|
||||
真实 Java `RegionSelectVo` 已明确 `regionCode`、`regionName`、`regionLevel` 等字段。个人资料当前仍没有可保存的地区字段,因此区划组件只提供级联、搜索和路径回显,不提交到资料更新接口。
|
||||
|
||||
### 7.6 家族圈
|
||||
|
||||
|
||||
Reference in New Issue
Block a user