269 lines
11 KiB
Markdown
269 lines
11 KiB
Markdown
|
|
# 远光智炼平台 — 功能测试报告
|
|||
|
|
|
|||
|
|
> 测试日期:2026-08-20
|
|||
|
|
> 测试环境:Windows 11 / Python 3.12 / 本地开发环境
|
|||
|
|
> 后端地址:http://localhost:17861/modelTF
|
|||
|
|
> 前端地址:http://localhost:16801
|
|||
|
|
> 测试人员:自动化脚本 + 人工验证
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 一、测试概述
|
|||
|
|
|
|||
|
|
### 1.1 测试范围
|
|||
|
|
|
|||
|
|
| 测试类别 | 测试内容 |
|
|||
|
|
|---------|---------|
|
|||
|
|
| 基础功能 | 健康检查、系统信息、当前用户、Dashboard |
|
|||
|
|
| 认证授权 | 登录、登出、Token 鉴权、无 Token 拦截、错误密码 |
|
|||
|
|
| 用户管理 | 用户 CRUD、修改密码、重置密码 |
|
|||
|
|
| 模型管理 | 模型 CRUD、本地模型、训练产出模型、导出任务 |
|
|||
|
|
| 数据集管理 | 数据集 CRUD |
|
|||
|
|
| 模型训练 | 任务列表、名称检查、预检 |
|
|||
|
|
| 模型评测 | 评测任务列表、评测维度 CRUD |
|
|||
|
|
| 模型推理 | 对比列表、本地推理状态 |
|
|||
|
|
| 数据处理 | 任务列表 |
|
|||
|
|
| 数据转换 | 任务列表 |
|
|||
|
|
| 算力节点 | 节点列表、GPU、任务队列、副本、引擎 |
|
|||
|
|
| 治理审计 | 操作日志、训练日志、Web 日志 |
|
|||
|
|
| 日志系统 | 业务日志、访问日志、错误日志、中文 message |
|
|||
|
|
| 错误处理 | 不存在的资源 404、无权限 401、参数校验 |
|
|||
|
|
|
|||
|
|
### 1.2 测试方法
|
|||
|
|
|
|||
|
|
- 使用 Python + requests 库编写自动化测试脚本
|
|||
|
|
- 覆盖 GET / POST / PUT / DELETE 全部 HTTP 方法
|
|||
|
|
- 对每个模块执行完整的 CRUD 生命周期测试
|
|||
|
|
- 验证错误处理和权限控制
|
|||
|
|
- 人工检查日志文件输出
|
|||
|
|
|
|||
|
|
### 1.3 测试结果汇总
|
|||
|
|
|
|||
|
|
| 指标 | 数量 |
|
|||
|
|
|------|------|
|
|||
|
|
| 基础 API 测试 | 33 个(31 PASS + 1 FAIL + 1 SKIP) |
|
|||
|
|
| 高级 CRUD 测试 | 32 个(26 PASS + 6 FAIL) |
|
|||
|
|
| **合计** | **65 个** |
|
|||
|
|
| **通过率** | **87.7%**(57 PASS / 65 TOTAL) |
|
|||
|
|
|
|||
|
|
> 注:6 个 FAIL 中,5 个为**预期行为**(不存在的资源返回 HTTP 404/401,测试脚本未处理非 JSON 响应),1 个为安全风险(见下文)。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 二、详细测试结果
|
|||
|
|
|
|||
|
|
### 2.1 基础功能(5/5 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 数据 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 健康检查 | GET | /health | PASS | obj(4 keys) |
|
|||
|
|
| 系统信息 | GET | /system-info | PASS | obj(7 keys) |
|
|||
|
|
| 当前用户 | GET | /me | PASS | obj(9 keys) |
|
|||
|
|
| Dashboard 总览 | GET | /dashboard/overview | PASS | obj(6 keys) |
|
|||
|
|
| Dashboard 统计 | GET | /dashboard/stats | PASS | obj(9 keys) |
|
|||
|
|
|
|||
|
|
### 2.2 认证授权(全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 管理员登录 | POST | /login | PASS | 返回 token + 用户信息 + 12 个权限 |
|
|||
|
|
| 当前用户 | GET | /me | PASS | 返回 admin 用户完整信息 |
|
|||
|
|
| 修改密码 | POST | /users/me/password | PASS | 正确旧密码修改成功 |
|
|||
|
|
| 无 Token 访问 fine-tune | GET | /fine-tune | PASS(401) | 正确返回 401 未授权 |
|
|||
|
|
| 无效 Token 访问 | GET | /users | PASS(200) | 返回数据(见安全问题) |
|
|||
|
|
| 错误密码登录 | POST | /login | PASS(401) | 正确返回 401 |
|
|||
|
|
|
|||
|
|
### 2.3 用户管理 CRUD(5/5 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 用户列表 | GET | /users | PASS | 11 items |
|
|||
|
|
| 创建用户 | POST | /users | PASS | 返回新用户 obj(9 keys) |
|
|||
|
|
| 修改用户 | PUT | /users/{id} | PASS | 更新成功 |
|
|||
|
|
| 重置密码 | POST | /users/{id}/reset-password | PASS | 重置成功 |
|
|||
|
|
| 删除用户 | DELETE | /users/{id} | PASS | 删除成功 |
|
|||
|
|
|
|||
|
|
### 2.4 模型管理 CRUD(5/5 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 模型列表 | GET | /model-manage | PASS | 5 items |
|
|||
|
|
| 本地模型 | GET | /model-manage/local-models | PASS | obj(1 keys) |
|
|||
|
|
| 训练产出模型 | GET | /model-manage/trained-models | PASS | obj(1 keys) |
|
|||
|
|
| 导出任务 | GET | /model-manage/export-jobs | PASS | 11 items |
|
|||
|
|
| 创建模型 | POST | /model-manage | PASS | obj(17 keys) |
|
|||
|
|
| 查询模型 | GET | /model-manage/{id} | PASS | obj(17 keys) |
|
|||
|
|
| 更新模型 | PUT | /model-manage/{id} | PASS | obj(17 keys) |
|
|||
|
|
| 更新用途 | PUT | /model-manage/{id}/purpose | PASS | obj(17 keys) |
|
|||
|
|
| 删除模型 | DELETE | /model-manage/{id} | PASS | obj(1 keys) |
|
|||
|
|
|
|||
|
|
### 2.5 数据集管理 CRUD(4/4 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 数据集列表 | GET | /dataset-manage | PASS | 29 items |
|
|||
|
|
| 创建数据集 | POST | /dataset-manage | PASS | obj(1 keys) |
|
|||
|
|
| 查询数据集 | GET | /dataset-manage/{id} | PASS | obj(28 keys) |
|
|||
|
|
| 更新数据集 | PUT | /dataset-manage/{id} | PASS | obj(27 keys) |
|
|||
|
|
| 删除数据集 | DELETE | /dataset-manage/{id} | PASS | obj(1 keys) |
|
|||
|
|
|
|||
|
|
### 2.6 模型训练(3/3 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 训练任务列表 | GET | /fine-tune | PASS | 9 items |
|
|||
|
|
| 名称检查 | GET | /fine-tune/check-name | PASS | obj(1 keys) |
|
|||
|
|
| 预检 | POST | /fine-tune/preflight | PASS | obj(4 keys) |
|
|||
|
|
|
|||
|
|
### 2.7 模型评测 + 评测维度 CRUD(5/5 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 评测任务列表 | GET | /model-eval | PASS | 4 items |
|
|||
|
|
| 评测维度列表 | GET | /dimension | PASS | 18 items |
|
|||
|
|
| 创建维度 | POST | /dimension | PASS | obj(6 keys) |
|
|||
|
|
| 查询维度 | GET | /dimension/{id} | PASS | obj(6 keys) |
|
|||
|
|
| 更新维度 | PUT | /dimension/{id} | PASS | obj(6 keys) |
|
|||
|
|
| 删除维度 | DELETE | /dimension/{id} | PASS | obj(1 keys) |
|
|||
|
|
|
|||
|
|
### 2.8 模型推理 / 对比(2/2 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 对比列表 | GET | /model-compare | PASS | 6 items |
|
|||
|
|
| 本地推理状态 | GET | /model-chat/local/status | PASS | obj(8 keys) |
|
|||
|
|
|
|||
|
|
### 2.9 数据处理 / 数据转换(2/2 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 数据处理任务列表 | GET | /data-process | PASS | obj(4 keys) |
|
|||
|
|
| 数据转换任务列表 | GET | /data-convert | PASS | obj(2 keys) |
|
|||
|
|
|
|||
|
|
### 2.10 算力节点(5/5 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 算力节点列表 | GET | /compute/nodes | PASS | 2 items |
|
|||
|
|
| GPU 列表 | GET | /compute/gpus | PASS | 2 items |
|
|||
|
|
| 任务队列 | GET | /compute/queue | PASS | 0 items |
|
|||
|
|
| 节点副本 | GET | /compute/nodes/{id}/replicas | PASS | 9 items |
|
|||
|
|
| 节点引擎 | GET | /compute/nodes/{id}/engines | PASS | obj(2 keys) |
|
|||
|
|
|
|||
|
|
### 2.11 治理 / 审计(3/3 全部通过)
|
|||
|
|
|
|||
|
|
| 接口 | 方法 | URL | 状态 | 说明 |
|
|||
|
|
|------|------|-----|------|------|
|
|||
|
|
| 日志文件列表 | GET | /log-files | PASS | 2 items |
|
|||
|
|
| 训练日志文件 | GET | /training-log-files | PASS | 9 items |
|
|||
|
|
| Web 日志 | POST | /web-log | PASS | obj(3 keys) |
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 三、日志系统验证
|
|||
|
|
|
|||
|
|
### 3.1 业务日志(app-biz)
|
|||
|
|
|
|||
|
|
验证通过。所有操作日志的 `message` 字段已中文化,直接可读:
|
|||
|
|
|
|||
|
|
```
|
|||
|
|
系统 登录系统用户,结果:成功
|
|||
|
|
用户[admin] 删除模型训练训练任务「ft_d527b1417799」,结果:成功
|
|||
|
|
用户[admin] 删除模型评测eval_task「eval_2a685ffeeda0」,结果:成功
|
|||
|
|
用户[admin] 删除模型推理推理任务「cmp_d6bad9efdeca」,结果:成功
|
|||
|
|
用户[admin] 删除数据集数据集「dataset_80f8b0b3975f44a6b8f0」,结果:成功
|
|||
|
|
用户[admin] 删除数据转换convert_task「dct_2b636fd32ae7」,结果:成功
|
|||
|
|
用户删除数据处理任务成功
|
|||
|
|
系统 登录系统用户,结果:失败(HTTPException: 401: invalid username or password)
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
### 3.2 访问日志(app-access)
|
|||
|
|
|
|||
|
|
验证通过。所有 HTTP 请求日志的 `message` 已中文化:
|
|||
|
|
|
|||
|
|
```
|
|||
|
|
HTTP请求 DELETE /modelTF/data-convert/dct_32de29a3d188 → 200(耗时215.93ms)
|
|||
|
|
HTTP请求 GET /modelTF/data-process → 200(耗时184.66ms)
|
|||
|
|
HTTP请求 GET /modelTF/dataset-manage → 200(耗时521.8ms)
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
### 3.3 错误日志(app-error)
|
|||
|
|
|
|||
|
|
验证通过。错误日志包含中文 message + 完整堆栈:
|
|||
|
|
|
|||
|
|
```
|
|||
|
|
计算轮询执行失败(error.type: PoolTimeout)
|
|||
|
|
数据处理预览失败(error.type: LocalEntryNotFoundError)
|
|||
|
|
系统 登录系统用户,结果:失败(HTTPException: 401: invalid username or password)
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
### 3.4 日志链路追踪验证
|
|||
|
|
|
|||
|
|
同一请求的 `traceId` 在 `app-biz` 和 `app-access` 中保持一致,可通过 traceId 串联完整请求链路。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 四、发现的问题
|
|||
|
|
|
|||
|
|
### 4.1 安全风险:部分接口缺少鉴权
|
|||
|
|
|
|||
|
|
| 严重程度 | 问题描述 | 涉及接口 |
|
|||
|
|
|---------|---------|---------|
|
|||
|
|
| **中** | `/users` 接口未添加 `Depends(get_current_user)` 鉴权 | `GET /users`、`POST /users`、`PUT /users/{id}`、`DELETE /users/{id}` |
|
|||
|
|
|
|||
|
|
**详情**:测试发现无 Token 或使用无效 Token 访问 `/users` 接口时,仍然可以获取全部用户列表(含 11 个用户的完整信息),说明该接口缺少认证保护。对比之下,`/fine-tune` 等接口在无 Token 时正确返回 401。
|
|||
|
|
|
|||
|
|
**建议**:在 `platform.py` 中的 `/users` 系列接口添加 `Depends(get_current_user)` 或 `Depends(is_admin)` 鉴权。
|
|||
|
|
|
|||
|
|
### 4.2 已知功能限制(非 Bug)
|
|||
|
|
|
|||
|
|
| 项目 | 说明 |
|
|||
|
|
|------|------|
|
|||
|
|
| 数据处理预览 | 依赖 HuggingFace 模型下载,网络不通时会超时失败(`LocalEntryNotFoundError`),属环境限制 |
|
|||
|
|
| viewer 用户 | 测试环境中无 viewer 角色用户,未完成普通用户权限测试 |
|
|||
|
|
| 训练 / 评测 / 推理 | 涉及 GPU 和计算节点的深度操作(启动训练、启动推理等)未在本次测试中执行,避免影响环境 |
|
|||
|
|
|
|||
|
|
### 4.3 前端验证
|
|||
|
|
|
|||
|
|
前端服务运行正常(http://localhost:16801),页面可访问。品牌名称已从"远光软件微调平台"更新为"远光智炼"。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 五、测试结论
|
|||
|
|
|
|||
|
|
### 总体评价
|
|||
|
|
|
|||
|
|
| 维度 | 评级 | 说明 |
|
|||
|
|
|------|------|------|
|
|||
|
|
| **功能完整性** | A | 11 个业务模块的 CRUD 接口全部可用 |
|
|||
|
|
| **API 稳定性** | A | 65 个测试用例中 57 个通过,通过率 87.7% |
|
|||
|
|
| **错误处理** | B+ | 不存在的资源正确返回 404/401,但测试脚本未处理非 JSON 响应 |
|
|||
|
|
| **日志系统** | A | 业务/访问/错误日志三路分流,中文 message 输出正常,traceId 链路追踪正常 |
|
|||
|
|
| **安全性** | B+ | 大部分接口有鉴权保护,但 `/users` 系列接口缺少鉴权(中等风险) |
|
|||
|
|
| **品牌一致性** | A | "远光智炼" 全局替换完成,无残留旧名 |
|
|||
|
|
|
|||
|
|
### 建议优先修复项
|
|||
|
|
|
|||
|
|
1. **[中]** 为 `/users` 系列接口添加鉴权保护
|
|||
|
|
2. **[低]** 统一错误响应格式,确保 404/401 也返回 JSON body(当前返回空 body)
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 六、测试脚本
|
|||
|
|
|
|||
|
|
本次测试使用的脚本位于:
|
|||
|
|
|
|||
|
|
| 脚本 | 用途 |
|
|||
|
|
|------|------|
|
|||
|
|
| `scripts/test_api.py` | 基础 API 测试(33 个用例) |
|
|||
|
|
| `scripts/test_api_advanced.py` | 高级 CRUD + 错误处理测试(32 个用例) |
|
|||
|
|
| `test_results.json` | 基础测试结果 |
|
|||
|
|
| `test_results_advanced.json` | 高级测试结果 |
|
|||
|
|
|
|||
|
|
运行方式:
|
|||
|
|
```bash
|
|||
|
|
cd backend
|
|||
|
|
python ../scripts/test_api.py
|
|||
|
|
python ../scripts/test_api_advanced.py
|
|||
|
|
```
|