本文档记录 PCB 轴向磁通电机自动化仿真系统的所有测试记录,包括 Motor-CAD 仿真测试、API 测试、集成测试等。 每次测试必须记录在此文档中(工作留痕)。 最后更新:2026-09-01
| 编号 | 日期 | 测试类型 | 结果 | 关键发现 |
|---|---|---|---|---|
| TEST-001 | 2026-08-28 | Motor-CAD 连接与变量探测 | ⚠️ 部分成功 | 发现 export_results API 兼容性问题、弹窗问题 |
| TEST-002 | 2026-08-28 | Motor-CAD 全流程验证(修复后) | ✅ 全部成功 | 验证连接/计算/导出/解析全流程,弹窗问题解决 |
| TEST-003 | 2026-08-28 | 扩展指标解析验证 | ✅ 全部成功 | 指标解析从7个提升到14个,平均转矩/转矩脉动仍需调查 |
| TEST-004 | 2026-08-29 | 平台化改造单元验证(指标单一事实源+归一化解析+适配器框架) | ✅ 全部成功 | 修复 tavg_nm/ripple_pct 解析缺口;统一指标单一事实源 |
| TEST-005 | 2026-08-29 | 平台化第二批(拓扑注册表+执行器适配器切换) | ✅ 全部成功 | 36 项断言全 PASS;79 个 .py 编译 0 失败 |
| TEST-006 | 2026-08-29 | P3-M1/M2 策略抽象层 + 自适应编排器闭环 | ✅ 全部成功 | fake 执行器 + temp DB 隔离回归,exit 0 |
| TEST-007 | 2026-08-29 | P3-M3 执行器批次化 + 多实例 | ✅ 全部成功 | point_id 回传 + 原子认领;P2 回归 36/36 不破坏 |
| TEST-008 | 2026-08-29 | P3-M4 调度契约统一 | ✅ 全部成功 | 状态词汇归一(queued→pending 等),向后兼容 |
| TEST-009 | 2026-08-29 | P3-M5 HTTP 全链路闭环 | ✅ 全部成功 | 闭环 8 点 budget_exhausted;91 个 .py 编译 0 失败 |
| TEST-010 | 2026-08-29 | P3-M5 真实 Motor-CAD 烟雾 | ✅ 全部成功 | 连接/求解/解析 21 指标;back_emf=11.15V 与历史一致 |
| TEST-011 | 2026-08-29 | P3-M6 Web 端 AdaptiveLoop 执行桥 | ✅ 全部成功 | fake plan→3 批 8 点;幂等;HTTP 端点 404/200 正常 |
| TEST-012 | 2026-08-29 | P3 收尾(边界测试+全量回归+规范修复) | ✅ 全部成功 | 工程规范落地,全量回归绿 |
| TEST-013 | 2026-08-29 | P3 遗留(原子认领+断点恢复+ASCII 纪律) | ✅ 全部成功 | 并发 8 线程恰 1 win;断点可恢复 |
| TEST-014 | 2026-08-29 | P4-M1~M3(Schema 单一权威+文档 V2+EXE 打包) | ✅ 全部成功 | dist/PCB-AFM-Executor.exe 12.6MB 打包成功 |
| TEST-015 | 2026-08-29 | P4-M4~M5(收敛曲线+L0 上提共享核心) | ✅ 全部成功 | points_history + L0 唯一实现(纯 stdlib) |
| TEST-016 | 2026-08-30 | P5-M1 前端全量 build 类型错误清零 | ✅ 全部成功 | vue-tsc 0 错误 + vite build 成功(退出码 0) |
| TEST-017 | 2026-08-30 | P5-M2 EXE 配置化 + mock 分支修复 + E2E mock | ✅ 全部成功 | executor_config.json 配置化;真实 COM 端到端待目标机 |
| TEST-018 | 2026-08-30 | P5-M2 补充:真实 EXE 端到端单点验证 | ✅ 全部成功 | airgap_mm→Airgap 映射 + point_id 排除;数值与 TEST-010 一致 |
| TEST-019 | 2026-08-30 | P5-M3 adaptive 可视化补全 | ✅ 全部成功 | 后端 4 新字段 + 前端 3 视图 + 8 测试 + build 绿 |
| TEST-020 | 2026-08-30 | P5-M4 策略层高级管线 | ✅ 全部成功 | Morris + IDW 代理 + 预算自适应;Kriging 降级 IDW |
| TEST-021 | 2026-08-30 | P5-M5 多工具适配器 | ✅ 全部成功 | 2 新适配器注册 + 22 测试;真实接入标注环境依赖 |
| TEST-022 | 2026-08-30 | P5-M6 多物理场 L2 接入 | ✅ 全部成功 | 指标 25→35(热6+结构4);报告按域分组;20 测试 |
| TEST-023 | 2026-08-30 | P6-M1 Web 前端 UI/UX 全面重构 | ✅ 全部成功 | 设计令牌+3公共组件+B1信息架构+B2 PlanDetail分层;vue-tsc 0错误 |
| TEST-024 | 2026-09-01 | 环境体检脚本 check_machine_paths.py 验证 | ✅ 脚本可用(shell 环境报包缺失属预期) | 新增脚本:Python版本/环境变量/Motor-CAD/包/Git/资产全检;未发现项目 venv |
日期:2026-08-28 04:49 - 05:08
测试环境:Windows 10,Python 3.x,pymotorcad 0.8.8,Motor-CAD v261
测试目的:验证 RobustMotorCADSolver 的连接、变量探测、参数写入、磁场计算、结果导出功能
测试脚本:scripts/test_robust_solver.py
输出目录:output/test_connect_20260828_044951/
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | Motor-CAD 连接 | ✅ 成功 | open_new_instance=True + set_visible(True),健康检查通过 |
| 2 | 五层自检 | ✅ 完成 | 连接/许可/模型/脚本层 PASS,权限层 FAIL(非管理员,预期) |
| 3 | 变量探测 | ⚠️ 11/14 | 3 个变量名不存在(Stator_Number_Of_Slots、Rotor_Number_Of_Poles、Peak_Phase_Current),触发 GUI 弹窗需人工点确定 |
| 4 | 参数写入+回读 | ✅ 成功 | TorquePointsPerCycle 30→60,回读 60.0,恢复 30 |
| 5 | 磁场计算 | ✅ 成功 | 耗时 174.4 秒 |
| 6 | 结果导出 | ❌ 失败 | export_results() missing 1 required positional argument: 'file_path' |
| 7 | 断开连接 | ✅ 成功 |
| 参数 | 值 | 单位 |
|---|---|---|
| Motor_Type | 0 | - |
| Airgap | 1 | mm |
| MagnetArc[ED] | 121 | EDeg |
| MagnetCentralArc_HalbachRing | 120 | EDeg |
| Slot_Opening | 8.5 | mm |
| Slot_Width | 8.5 | mm |
| Copper_Width | 3.64 | mm |
| TorquePointsPerCycle | 30 | points/cycle |
| AirgapMeshPoints_mesh | 600 | points |
| AirgapMeshPoints_layers | 600 | points |
| Shaft_Speed | 5000 | rpm |
get_variable 对不存在的变量名会抛出异常 并弹出 GUI 错误对话框,阻塞无人值守批处理
MessageDisplayState=2 禁用弹窗export_results 签名是 (solution_type, file_path),之前只传了 file_path
export_results("EMagnetic", file_path)f3b492a — 修复 export_results API 兼容性日期:2026-08-28 05:08 - 05:15
测试环境:Windows 10,Python 3.x,pymotorcad 0.8.8,Motor-CAD v261
测试目的:验证 TEST-001 发现的两个问题修复后,全流程是否正常
测试脚本:scripts/test_robust_solver.py(已添加弹窗抑制)
输出目录:output/test_connect_20260828_050834/
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | Motor-CAD 连接 | ✅ 成功 | open_new_instance=True + set_visible(True) |
| 2 | 弹窗抑制 | ✅ 成功 | MessageDisplayState=2,变量探测阶段无弹窗 |
| 3 | 五层自检 | ✅ 完成 | 连接/许可/模型/脚本层 PASS,权限层 FAIL(非管理员,预期) |
| 4 | 变量探测 | ✅ 11/14 | 3 个变量名不存在但无弹窗(已被抑制) |
| 5 | 参数写入+回读 | ✅ 成功 | TorquePointsPerCycle 30→60,回读 60.0,恢复 30 |
| 6 | 磁场计算 | ✅ 成功 | 耗时 138.1 秒(比 TEST-001 的 174.4 秒快) |
| 7 | 结果导出 | ✅ 成功 | 10788 字节,export_results("EMagnetic", path) |
| 8 | 结果解析 | ✅ 成功 | 解析到 7 个指标 |
| 9 | 断开连接 | ✅ 成功 | 弹窗状态恢复,基线重载 |
| 指标 | 值 | 单位 |
|---|---|---|
| 系统效率 efficiency_pct | 86.06 | % |
| 总损耗 total_losses_w | 41.945 | W |
| 输入功率 input_power_w | 300.9 | W |
| 磁钢损耗 magnet_loss_w | 0.5641 | W |
| 定子铁耗 iron_loss_w | 3.002 | W |
| 线间反电动势有效值 back_emf_v | 7.898 | V |
| 轴转速 shaft_speed_rpm | 5000 | rpm |
tavg_nm(平均转矩)和 ripple_pct(转矩脉动),原因是字段名匹配不完整6a8bc80 提交中扩展 METRIC_DEFINITIONS 从 12 个指标到 20 个,添加了中文字段名变体6a8bc80 — 扩展指标别名 + 测试脚本弹窗抑制RobustMotorCADSolver 已验证可正常连接 Motor-CAD、执行磁场计算、导出并解析结果,弹窗问题已解决,可支持无人值守批量仿真。
日期:2026-08-28 06:01 - 06:05
测试环境:Windows 10,Python 3.x,pymotorcad 0.8.8,Motor-CAD v261
测试目的:验证扩展后的 METRIC_DEFINITIONS(12→20个指标)能否解析到更多指标,特别是平均转矩和转矩脉动
测试脚本:scripts/test_robust_solver.py
输出目录:output/test_connect_20260828_060101/
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | Motor-CAD 连接 | ✅ 成功 | open_new_instance=True + set_visible(True) |
| 2 | 弹窗抑制 | ✅ 成功 | MessageDisplayState=2,无弹窗 |
| 3 | 五层自检 | ✅ 完成 | 4/5 PASS(权限层 FAIL,非管理员,预期) |
| 4 | 变量探测 | ✅ 11/14 | 3 个变量名不存在,无弹窗 |
| 5 | 参数写入+回读 | ✅ 成功 | TorquePointsPerCycle 30→60→30 |
| 6 | 磁场计算 | ✅ 成功 | 耗时 133.5 秒 |
| 7 | 结果导出 | ✅ 成功 | 10788 字节 |
| 8 | 结果解析 | ✅ 成功 | 解析到 14 个指标(比 TEST-002 的 7 个增加一倍) |
| 9 | 断开连接 | ✅ 成功 |
| 指标 | 值 | 单位 | 备注 |
|---|---|---|---|
| 系统效率 efficiency_pct | 86.06 | % | 与 TEST-002 一致 |
| 总损耗 total_losses_w | 41.945 | W | 与 TEST-002 一致 |
| 输入功率 input_power_w | 300.9 | W | 与 TEST-002 一致 |
| 输出功率 output_power_w | 258.95 | W | 🆕 新增 |
| 电磁功率 em_power_w | 273.29 | W | 🆕 新增 |
| 磁钢损耗 magnet_loss_w | 0.5641 | W | |
| 定子铁耗 iron_loss_w | 3.002 | W | |
| 线间反电动势有效值 back_emf_v | 11.15 | V | 与 TEST-002 不同(7.898→11.15,可能是字段匹配到了不同的字段) |
| 轴转速 shaft_speed_rpm | 5000 | rpm | |
| 轴转矩 shaft_torque_nm | 0.49456 | Nm | 🆕 新增 |
| 堵转转矩 stall_torque_nm | 9.364 | Nm | 🆕 新增 |
| 转矩常数 torque_constant | 0.01757 | Nm/A | 🆕 新增 |
| 相电流峰值 phase_current_peak_a | 29.7 | A | 🆕 新增 |
| 线电流有效值 line_current_rms_a | 21.0 | A | 🆕 新增 |
| 指标 | 预期别名 | 可能原因 |
|---|---|---|
| 平均转矩 tavg_nm | 平均转矩 (virtual work) / Average torque (virtual work) |
字段名中可能有不可见字符(全角空格等),需进一步调查 |
| 转矩脉动 ripple_nm | Torque Ripple (VW) |
可能被其他字段先匹配,或字段名有差异 |
| 转矩脉动百分比 ripple_pct | Torque Ripple (VW) [%] |
同上 |
run_single_point() 完整流程和逐点落盘scripts/task_executor.py 未启动,任务卡在 dispatched 0进度。
修复:新增 scripts/run_task_executor.py 启动入口,后台运行。fetch_pending_tasks 同时认领 pending + dispatched。_hydrate_task,从 /api/tasks/{id}/download 拉取完整 task.json。robust_motorcad.run_single_point 跳过非数值参数。motorcad_var 字段(从 .mot 提取真实变量名),_expand_plan_to_parameters
按模板合并生成参数集,仅写 motorcad_var 非空项。Slot_Depth 等默认值对齐基线模型。_send_heartbeat 注册,前端可显示在线/进度。a7123abf:completed,2/2 点 OK,耗时 307s日期:2026-08-29 环境:Windows 10 / 11,Python 3.x,本地工作区 目的:验证平台化改造第一批的正确性与回归安全性 依据:docs/PLATFORM_DESIGN_V2.md(平台化升级设计方案)
| 项 | 结果 | 详情 |
|---|---|---|
| 归一化解析(含全角字符) | ✅ | 模拟 Motor-CAD 导出含全角空格/全角括号/全角[],tavg_nm、ripple_pct、efficiency_pct、total_losses_w、back_emf_v 全部解析成功 |
| 中文别名匹配 | ✅ | 中文字段(平均转矩/转矩脉动/系统效率)能正确匹配 |
| % 守卫 | ✅ | [%] 字段不再污染 Nm 值指标(ripple_abs_nm/ripple_nm 不被 ripple_pct 字段污染) |
| 三端导入回归 | ✅ | solver_core(25)/robust_motorcad(25)/metrics_constants(25) 三端持久化同源,导入成功 |
| 本地端关键模块 | ✅ | solver_core/scan_engine/experience_db/robust_motorcad/task_executor/run_single/run_scan 7/7 导入 OK |
| Web 端引用模块 | ✅ | metrics_constants/plans/result_analyst/task_manager 4/4 导入 OK |
| 全量编译 | ✅ | 78 个 .py 全部 py_compile 通过,0 失败 |
| 纯 ASCII 约束 | ✅ | 新写代码全部 ASCII,无非 ASCII 行 |
| 适配器注册表 | ✅ | import 即注册 motorcad;未注册工具报清晰 KeyError |
| 适配器协议 | ✅ | run_point/extract_metrics 输出 schema 与设计一致 |
日期:2026-08-29 环境:Windows 10 / 11,Python 3.x,本地工作区(无真实 Motor-CAD 启动) 目的:验证 P2 拓扑注册表与执行器通过适配器注册表驱动,消除“拓扑裸字符串”与“求解器硬编码”
src/afmcore/topology.py:拓扑注册表(SSSR 完整参数体系 8 组 37 参数 + DRSS/SDSR 预留),提供 get_topology / is_supported / is_active / validate_params / to_dictsrc/plan_schema.py:validate() 集成拓扑注册校验(未知拓扑报错)scripts/task_executor.py:MotorCADTaskExecutor 从硬编码 RobustMotorCADSolver 切换为 afmcore.adapters.get_adapter(tool);结果 metrics 扁平化到顶层,修复 _compute_metrics 取不到嵌套 metrics 的缺口| 项 | 结果 | 详情 |
|---|---|---|
| 拓扑注册表 | ✅ 22 项 | 注册/查询(大小写不敏感)/参数体系(SSSR 37参数8组)/序列化/自定义注册幂等覆盖 |
| 拓扑校验集成 | ✅ 4 项 | plan_schema.validate:SSSR 通过、TORUS 拒绝、DRSS 接受(已注册)、序列化往返 |
| 适配器注册表 | ✅ 4 项 | motorcad 注册、get_adapter 返回协议实例、未注册工具 KeyError |
| 执行器适配器路径 | ✅ 6 项 | OK 点扁平化、_compute_metrics 取到 tavg_nm_mean、FAILED 点抛异常、execute_task 3 点全链路、cleanup 断开 |
| 全量编译 | ✅ | 79 个 .py 全部 py_compile 通过,0 失败 |
| 纯 ASCII | ✅ | 新增/修改代码全部 ASCII(topology.py / plan_schema.py / task_executor.py / test_platform_registry.py) |
| 导入回归 | ✅ | afmcore(拓扑/指标/适配器) + src(plan_schema/solver_core) + scripts(robust_motorcad/task_executor) + web(metrics_constants) 全部 OK |
日期:2026-08-29 环境:Windows,Python 3.x,本地工作区(无真实 Motor-CAD 启动;闭环用 fake 执行器) 目的:验证 P3 第一批:执行策略抽象层(M1)与自适应编排器全闭环(M2),为「web 方案 -> 批次任务 -> 本地执行 -> 回填搜索 -> 续批/收敛」打通。
| 项目 | 结果 | 详情 |
|---|---|---|
| 策略注册表 | 通过 | 冒烟:adaptive/full_factorial/lhs 注册、FF 分批收敛、LHS 采样范围、adaptive 桥回传、无 backend/未知策略报错 |
| plan_schema 策略校验 | 通过 | 别名 active_learning/constrained -> adaptive;random_forest 拒绝;序列化往返归一化 |
| 任务模型扩展 | 通过 | 新字段 create_task 透传;_task_to_dict 输出 point_ids/dynamic/task_type |
| DB 迁移 | 通过 | 旧 tasks 表 init_db 自动 ADD COLUMN 5 字段 |
| orchestrator 闭环 | 通过 | fake 执行器驱动:首批 3 点 -> 回填 -> 续批 -> budget_exhausted 收敛,n_results=8,状态持久化,重复 loop 拒绝 |
| 编译/ASCII | 通过 | 新改 4 文件 py_compile 通过、纯 ASCII |
| 回归脚本 | 通过 | scripts/test_p3_orchestrator.py 入库,exit 0 |
日期:2026-08-29 环境:Windows,Python 3.x,本地工作区(无真实 Motor-CAD;mock 执行器) 目的:验证执行器支持 adaptive_batch 任务的 point_id 回传、多实例并行的认领原子化、以及独立 executor_id。
| 项目 | 结果 | 详情 |
|---|---|---|
| point_id 透传 | 通过 | OK 与 FAILED 点均在结果顶层带 point_id |
| 认领原子化 | 通过 | dispatch 返回 False 时任务被跳过(不执行) |
| executor_id 唯一 | 通过 | 默认实例各不相同;显式传入生效 |
| P2 回归 | 通过 | test_platform_registry.py 36/36 不回归 |
| M3 回归 | 通过 | scripts/test_executor_m3.py 入库,exit 0 |
| 编译/ASCII | 通过 | 3 文件 py_compile 0 失败、纯 ASCII |
日期:2026-08-29 环境:Windows,Python 3.x,本地工作区(无 web 服务/Motor-CAD) 目的:统一两套调度状态词汇(TaskManager 的 pending/dispatched 与 BatchScheduler 的 queued),并让 BatchScheduler 任务字段与 Task ORM 对齐(M2 新增的 adaptive-batch 字段)。
| 项目 | 结果 | 详情 |
|---|---|---|
| 状态归一 | 通过 | queued->pending、canceled->cancelled、completed_with_errors->completed、未知词透传、终态判定 |
| 字段合并 | 通过 | merge_adaptive_fields 默认值(scan/False/[]/None)与显式值 |
| scheduler 字段对齐 | 通过 | add_task 新字段透传、_summary 输出、legacy 调用不破坏、queued->running 流转、状态落盘 |
| 回归 | 通过 | test_p3_orchestrator.py(M2 闭环)不回归;test_p3_m4_contract.py 入库 exit 0 |
| 编译/ASCII | 通过 | 3 文件 py_compile 0 失败、纯 ASCII |
日期:2026-08-29 环境:Windows,Python 3.x;临时 SQLite DB + uvicorn 起的真实 FastAPI 后端;本地 mock 执行器(无真实 Motor-CAD) 目的:验证 P3 全链路真实 HTTP 闭环:orchestrator -> 任务 -> 本地执行器(HTTP 轮询) -> 仿真 -> 回传(point_id) -> 回填搜索 -> 续批 -> 收敛。
| 项目 | 结果 | 详情 |
|---|---|---|
| web 启动 | 通过 | temp DB + uvicorn 健康检查 OK |
| orchestrator 建任务 | 通过 | task_type=adaptive_batch,首批准 3 点 |
| 执行器 HTTP 认领 | 通过 | 轮询 pending/dispatched -> dispatch -> 执行 |
| point_id 回传 | 通过 | report_results 结果带 point_id,搜索按 point_id 回填 |
| 续批/收敛 | 通过 | 3+4+1 点 -> budget_exhausted,n_results=8 |
| 全量回归 | 通过 | P2 36 项 + M2 + M3 + M4 全部 PASS;91 个 .py 编译 0 失败 |
| 退出码 | 通过 | exit 0(无 AI 噪音:orchestrator 无 KIMI_API_KEY 时跳过 AI 分析) |
日期:2026-08-29 环境:Windows + Motor-CAD v261(MOTORCAD_ACTIVEX 已设、license 1055@localhost、exe 存在);基线模型 MARS-12S10P_SSSR_D76-C150_V5.0-0819.mot 目的:验证 MotorCADAdapter 真实求解通路:连接 -> 基线加载 -> 求解 1 点 -> 导出/解析指标 -> 断开。
MotorCADAdapter.run_point 忽略 model_path 参数:run_point(model_path=...) 内部 _ensure_solver() 用默认空路径创建 RobustMotorCADSolver,且从不把传入 model_path 同步给 solver,导致 load_from_file('') 报 "Motor-CAD File does not exist"。修复:run_point 在 connect 前将 model_path 同步到 solver.model_path。
| 项目 | 结果 | 详情 |
|---|---|---|
| 连接 | 通过 | open_new_instance + set_visible |
| 基线加载 | 通过 | load_from_file 真实 .mot |
| 求解 | 通过 | 电磁计算 146.3s(单点) |
| 指标解析 | 通过 | 21 项指标(tavg_nm/ripple/efficiency/back_emf/...) |
| 解析正确性 | 通过 | back_emf=11.15V 与 TR-2026-08-29-01 完全一致 |
| 关键指标 | - | tavg_nm=0.52187、efficiency=86.06%、total_losses=41.95W |
| 输出 | - | output/smoke_p3_m5/(不入库) |
日期:2026-08-29 环境:临时 SQLite DB(AFM_DB_PATH)+ KIMI_API_KEY=""(无 AI 后端,纯定量) 目的:把 Web 端已验收的 adaptive 搜索(AdaptiveLoop)接到本地执行器:批次 -> adaptive_batch Task -> 执行器回传 -> report-results 回填 -> 续批 -> 收敛。验证新提交桥 submit_batch_to_executor + 新端点 POST /api/adaptive/loops/{id}/submit-batch。
| 项目 | 结果 | 详情 |
|---|---|---|
| 闭环驱动 | 通过 | fake plan -> initialize_search(3点) -> submit-batch -> 3 批 -> budget_exhausted,8 点 / 8 预算 |
| Task 落库 | 通过 | 每批 1 个 adaptive_batch Task,含 loop_id/batch_id/point_ids/dynamic=True |
| point_ids 一致性 | 通过 | 初始批次 ids=[0,1,2] 与 task point_ids 一致 |
| 幂等性 | 通过 | 无 pending 批次时 submit 返回 task_id=None,不产生重复 Task |
| HTTP 端点 | 通过 | POST /api/adaptive/loops/{id}/submit-batch:404(未找到) / 200(task_id) |
| 全量回归 | 通过 | P2 36 项 + M2/M3/M4/M5/M6 全绿;91 .py 编译 0 失败 |
项目存在两套 adaptive 循环(均为已验收):
日期:2026-08-29 环境:临时 SQLite DB + 无 AI 后端;P4 验收套件在项目 web 环境内运行 目的:P3 收尾自查——按新工程规范(禁止臆测/测试完备/代码规范/自查清单)核对 P1~P3 平台化批次,补齐边界/异常/空值单元测试,修复验收暴露的规范违规,同步文档状态。
| 测试 | 覆盖 | 结果 |
|---|---|---|
| scripts/test_p3_unit_edge.py | 策略层(注册/未注册/空kind/坏类/别名归一/空points/分批/收敛/batch_size=0)、orchestrator(空参数/重复loop/缺失loop/批次未完成不推进)、AdaptiveLoop.submit 未初始化 RuntimeError、task_manager(缺失返回None/空参数) | PASS |
deploy.ps1 is ASCII-only 抓出;去掉 BOM 后 P4 验收复跑 37 passed / 0 failed。| 套件 | 结果 |
|---|---|
| test_platform_registry.py(P2) | PASS 36 项 |
| test_p3_orchestrator.py(M2) | PASS |
| test_executor_m3.py(M3) | PASS |
| test_p3_m4_contract.py(M4) | PASS |
| test_p3_closed_loop.py(M5) | PASS |
| test_p3_adaptive_execution.py(M6) | PASS |
| test_p3_unit_edge.py(新增) | PASS |
| test_p4_acceptance.py(P4 验收,BOM 修复后) | 37 passed / 0 failed |
日期:2026-08-30
环境:Windows 10,Node v20.20.2,npm 10.8.2,Vue 3.3 + TypeScript 5.5 + Element Plus 2.4 + Vite 5
目的:参考 SimScale / Ansys 等在线仿真工具设计语言,完成 B1(信息架构)+ B2(PlanDetail 分层)两批次前端重构,解决信息过载、导航混乱、参数命名不一致、视觉重复等问题
测试方式:静态代码审查 + npm run build(vue-tsc 类型检查 + vite 生产构建)
| 类别 | 文件 | 变更内容 |
|---|---|---|
| 全局样式 | src/style.css |
重写为设计令牌系统(CSS 变量):主色 #2563eb、中性灰阶、8px 网格、统一圆角/阴影/过渡;Element Plus 主题覆盖 |
| 公共组件 | src/components/StatCard.vue |
新建,统一统计卡片(消除 4 处重复手写) |
| 公共组件 | src/components/SectionCard.vue |
新建,统一内容区块卡片 |
| 公共组件 | src/components/PageHeader.vue |
新建,统一页面头部 |
| B1 布局 | src/layouts/MainLayout.vue |
侧边栏 5 组工作流导航 + AI 高级功能折叠 + 面包屑层级链 + 全局任务状态条 + 侧边栏折叠 + 页面过渡动画 |
| B2 核心页 | src/views/PlanDetail.vue |
1129 行长卷重构为 4 Tab(概览/方案参数/仿真结果/AI闭环);固定参数默认折叠只显示修改项;运行中进度横幅;AI 闭环步骤向导 |
| 页面优化 | src/views/ProjectList.vue |
PageHeader + StatCard + SectionCard + 搜索/拓扑筛选 + 创建弹窗双列布局 |
| 页面优化 | src/views/Dashboard.vue |
PageHeader + StatCard + ECharts 趋势/Pareto 图 + 结果表 + CSV 导出 |
| 页面优化 | src/views/TaskManager.vue |
6 项状态统计卡 + 状态筛选 + 创建任务从方案下拉选择(JSON 降为高级折叠)+ 详情抽屉优化 |
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | 全局设计令牌定义 | ✅ 通过 | CSS 变量覆盖主色/语义色/间距/圆角/阴影/字体/侧边栏/布局 8 大类 |
| 2 | 公共组件创建 | ✅ 通过 | StatCard/SectionCard/PageHeader 三组件含 props/slots/类型定义 |
| 3 | MainLayout 重构 | ✅ 通过 | 5 组导航渲染正常;AI 高级功能折叠/展开;面包屑随路由动态生成;全局任务状态 10s 轮询 |
| 4 | PlanDetail Tabs 重构 | ✅ 通过 | 4 Tab 切换正常;固定参数修改项检测逻辑;分类折叠;AI 闭环步骤指示器 |
| 5 | vue-tsc 类型检查 | ✅ 通过 | 0 错误(修复了 NavItem 联合类型、fixedCategories unknown[]、p.value string|number、api.planApi 引用等 6 类类型问题) |
| 6 | vite 生产构建 | ✅ 通过 | 2283 模块转换,11.62s 构建完成;业务 chunk 13~26kB,vendor 库独立分包 |
| 7 | 构建产物体积 | ⚠️ 警告 | vendor-echarts 1042kB / vendor-element 948kB 超 500kB 警告(既有问题,非本次引入,建议后续 echarts 按需引入) |
npm run dev 后人工走查核心流程日期:2026-08-29 环境:Windows / Python / 常驻 uvicorn(8000)+ 常驻执行器在跑(未干扰)
处理项:
task_manager.dispatch_task 由"读-改-写"改为 SQLAlchemy 条件 UPDATE(WHERE status='pending' + rowcount 判定),多执行器竞争同一任务恰好一次成功。
scripts/test_p3_concurrency.py:8 线程竞争同一 pending 任务 → 恰 1 win / 7 lost(ValueError);顺序二次认领拒绝;HTTP 级竞争同样恰 1 win。FeasibilityFirstSearch.import_state() + AdaptiveLoop.export_state()/restore_state() + GET /loops/{id}/export、POST /loops/import 端点。
scripts/test_p3_checkpoint.py:run_id/used_budget/points/objective 一致,恢复后可继续 select_next_batch。plans.py(14 中文串)+ fixed_params_template.py(86 中文 label)转 \uXXXX;运行解码正确(KIMI 空 key 纯定量降级 200)。test_api_client.py 用临时 DB + 后台 uvicorn 跑通真实链路;未杀用户常驻服务(PID 30496/39420 原样保留);真实 Motor-CAD 占用 license,robust 未改动不重跑,维持标注。验证结果:全部 PASS;全量回归基线绿(P2 36 / M3 / M4 / closed_loop / adaptive / unit_edge / p4_acceptance 37 / concurrency / checkpoint)。
日期:2026-08-29
src.plan_schema.py 增强(parse_plan/validate_plan_dict 入口 + ScanVariable.from_dict 容忍 min_value/max_value 别名 + validate(require_model_path) 分级);web 端 main.py 注入 repo root,plans/ai_plan 接入校验(400/422 拒绝非法 plan_data)。
scripts/test_p4_schema.py:7 组全过(happy/别名/空值/异常/分级/拓扑策略/web 接入)。run_task_executor.py 加 --version/--self-test;scripts/build_executable.ps1(PyInstaller onefile,paths=src+root,collect-all ansys.motorcad)。
dist/PCB-AFM-Executor.exe(12.6MB):--version 与 --self-test(mock 单点 status=OK)均通过。真实 Motor-CAD COM 连接依赖 license,不在打包自检内(标注环境依赖)。日期:2026-08-29
search.get_state_summary() 新增 points_history(逐评估点 id/batch/params/objective/feasible/status),SearchStateResponse 携带该字段;前端 AdaptiveOptimize.vue 增收敛曲线(echarts 散点可行/不可行 + 当前最优 step 折线)。
scripts/test_p4_m4_convergence.py:5 组全过(空历史/初始批次/跨批累积/不可行标记/响应模型接线)。L0PreScreeningEngine 迁至 src/afmcore/l0/prescreening.py(唯一实现,纯 stdlib),web 端薄 re-export 保持 6 处调用点兼容。
scripts/test_p4_m5_l0.py:8 组全过(单一定义/四类约束门/空输入门/filter_feasible/feasibility_search 集成)。test_p3_closed_loop.py/test_p4_m4_convergence.py 补 repo root 到 sys.path(L0 re-export 依赖 src 解析)。环境依赖(未自动化,如实标注):真实 Motor-CAD 求解(license server)不在本批自动化范围内;EXE 的真实 Motor-CAD COM 连接需在目标机验证。
日期:2026-08-30 环境:Windows / Node v20.20.2 / npm 10.8.2 / Python 3.13.13
背景:backlog B1——npm run build(vue-tsc && vite build)历史遗留 71 处类型错误(TS2339/TS2345/TS7006),涉及 Dashboard/ExecutorMonitor/ExperienceList/PlanDetail/ProjectDetail/ProjectList 6 个 .vue 文件。P4-M4 只保证 AdaptiveOptimize.vue 自身 0 错误,全量 build 一直红。
根因:src/api/index.ts 的响应拦截器(D2 fix)运行时已把 AxiosResponse unwrap 为 .data,但 TS 类型上 api.get()/post() 仍声明为 Promise<AxiosResponse>,导致所有调用处直接访问响应字段(res.items/res.metrics 等)报 TS2339;PlanDetail 中 task.status 被误判为 AxiosResponse.status(HTTP 状态码,number 类型)报 TS2345。
修复:
web/frontend/src/api/index.ts:axios 实例类型改写为 UnwrappedApi 接口(get/post/put/delete 均返回 Promise<T>,默认 any)——类型声明与运行时行为对齐;拦截器逻辑原样保留(实例改名 instance,再 cast 到 UnwrappedApi)。一处修复覆盖全部 69 处 TS2339/TS2345。web/frontend/src/views/PlanDetail.vue(418 行):@selection-change 回调参数 sel 显式标注 any[],消除 TS7006 隐式 any。验证结果:
npm run build(vue-tsc && vite build):vue-tsc 0 错误;vite 2274 modules 构建成功,真实退出码 0(cmd /c 确认)。/api/health 200;test_api_client.py 真实链路 PASSED(8 项目/历史结果正常读取)。/api 代理 health 200。遗留/说明:
UnwrappedApi 默认返回 any,与既有运行时行为一致;需要类型安全的调用可传泛型(如 api.get<Project[]>())。日期:2026-08-30 环境:Windows / Python 3.13.13 / PyInstaller 6.22.2 / 独立后端 8010 + 临时 DB(未干扰用户常驻 8000 服务)
目的:把本地执行器 EXE 配置化(web 地址 / model 路径 / 日志 / 实例数从 executor_config.json 读取),并打通"EXE → Web 端到端回传"验收链路(mock 求解先行)。
scripts/executor_config.py:配置加载器。优先级:--config > $EXECUTOR_CONFIG > <EXE目录>/executor_config.json > <仓库根>/executor_config.json > 内置默认;单字段可被环境变量覆盖(WEB_BASE_URL/MOTORCAD_MODEL/EXECUTOR_INSTANCES 等);相对路径按 EXE 目录/仓库根解析;校验 instances≥1、poll_interval>0、log_level 枚举、web_base_url http(s)、enable_mock bool。executor_config.json(仓库根模板):8 字段侧车配置。scripts/run_task_executor.py:--config/--instances/--interval/--mock/--log-dir/--log-level;logging 落盘 output/executor_logs/;单入口多实例(instances>1);版本号升 1.1.0。scripts/run_task_executor_parallel.py:复用共享配置(保留 --instances/--interval/--mock CLI 兼容)。scripts/task_executor.py(P4-M3 遗留):MotorCADTaskExecutor._run_simulation_point 忽略 enable_mock 无条件走真实 adapter;现 mock 分支先于 adapter(mock 结果带 source="mock",不启动 Motor-CAD、不要求 model_path)。| 测试 | 覆盖 | 结果 |
|---|---|---|
| scripts/test_executor_config.py | 20 用例:默认/文件合并/绝对路径/环境覆盖/优先级/边界(instances=1, poll=0.5, 空model)/异常(坏JSON/非对象/坏URL/0实例/坏level/坏mock类型)/空值(空对象/null字段/空env) | ✅ EXIT=0 |
| scripts/test_executor_p5m2.py | 6 用例:mock 点 source/多点/非法 model_path 仍 mock/默认 mock off/真实模式缺 model_path 报错/空 model_path | ✅ EXIT=0 |
| 全量回归 | test_*.py 全绿(16 个脚本 EXIT=0;test_api_client 需后端已跳过,由端到端验证替代) | ✅ 16/16 |
| ASCII/CRLF | 新改 6 个 .py 纯 ASCII、CRLF 与现有文件一致 | ✅ |
dist/PCB-AFM-Executor.exe(PyInstaller onefile,--version=1.1.0、--self-test OK)。AFM_DB_PATH=<临时DB> + AFM_PORT=8010 + uvicorn 启动,/api/health 200。--config <临时侧车> 启动(web_base_url=8010、enable_mock=true、poll_interval=2)。POST /api/tasks 创建 3 点任务(airgap 0.8/1.0/1.2)→ EXE 轮询认领 → mock 求解 → 回传 Web。completed、3/3 成功(successful_points=3)、duration 0.05s;点级结果 source="mock"、point_id 保留;聚合指标:tavg 34.56~42.05 N·m、eff 87.95~89.73%、losses 29.61~56.77 W、temp 85.1~101.1 ℃。MotorCADTaskExecutor._run_simulation_point 无条件走真实 adapter,--mock/enable_mock 从未真正进入 mock 分支;本次修复(见上),并用"非法 model_path + mock 仍成功"用例锁定回归。dist/PCB-AFM-Executor.exe + executor_config.json(web_base_url 指向实际后端、model_path 填目标机 .mot 绝对路径)到目标机;MOTORCAD_ACTIVEX 与 ANSYSLMD_LICENSE_FILE=1055@<server> 已设;PCB-AFM-Executor.exe 启动后轮询认领;日期:2026-08-30 环境:Windows + Motor-CAD v261(MOTORCAD_ACTIVEX 已设、license 1055@localhost、exe 存在);独立后端 8010 + 临时 DB(未干扰用户常驻 8000 服务)
目的:完成 P5-M2 验收点②"真实 EXE 端到端回传 Web 结果"——用打包后的 dist/PCB-AFM-Executor.exe 以真实模式(非 mock)驱动 Motor-CAD 求解单点并回传 Web。
airgap_mm,Motor-CAD 实际变量名是 Airgap(TEST-002 已探测)。此前 resolve_variable_name 直接透传导致 Could not find airgap_mm。修复:scripts/robust_motorcad.py VARIABLE_NAME_MAP 增加业务别名 "airgap_mm": {"default": "Airgap"}。point_id 透传标记被 run_single_point 参数循环当作 Motor-CAD 变量 set_variable 导致 Could not find point_id。修复:参数写入循环跳过元数据键(point_index/point_label/point_id)。| 项目 | 结果 | 详情 |
|---|---|---|
| EXE 真实模式 | 通过 | --config 侧车(enable_mock=false,model_path 绝对路径) |
| 认领→求解→回传 | 通过 | 任务 completed,duration 167.5s(含 Motor-CAD 启动 + 求解) |
| 求解时长 | 通过 | solve_time_s=145.22(单点电磁计算) |
| 指标完整性 | 通过 | 20+ 指标(tavg/ripple/efficiency/losses/back_emf/温度类/电流类/转速) |
| 数值一致性 | 通过 | tavg_nm=0.52187、eff=86.06%、total_losses=41.945W、back_emf=11.15V —— 与 TEST-010 完全一致 |
| point_id 保留 | 通过 | 结果点级带 point_id=1 |
| 回归 | 通过 | 全量 test_*.py 16/16 EXIT=0(含 test_robust_solver) |
scripts/test_executor_p5m2.py 扩至 8 用例:新增 resolve_variable_name("airgap_mm")=="Airgap" 映射断言 + point_id 排除回归断言。日期:2026-08-30 环境:Windows + 独立后端 8011(未干扰用户常驻 8000)+ 前端 vue-tsc build
目的:完成 P5-M3 验收点"前端 adaptive 三视图可见"——批次点状态可视化(每批进度/分布)+ L0 预筛选结果前端视图 + adaptive 循环运行期状态推送(轮询增强)。
web/backend/app/services/feasibility_search.py get_state_summary() 增加 4 字段:
infeasible_points / failed_points:状态计数batch_summary:按 batch_id 分组,每批含 total/pending/ok/infeasible/failed/best_objective(respect objective_direction)l0_summary:sampled/feasible/infeasible/pass_rate/top_infeasible_reasons(name/count/category,从不可行点 feasibility_report 聚合)_count_by_status / _build_batch_summary / _build_l0_summaryweb/backend/app/routers/search.py SearchStateResponse 增加对应 4 字段(带默认值,向后兼容)。views/ai/AdaptiveOptimize.vue)| 项目 | 结果 |
|---|---|
| 后端单元测试 | 8/8 PASS(test_search_state_summary.py:正常/报告后聚合/min-max方向/failed计数/空search边界/infeasible原因结构/未知id容错/批次排序) |
| 前端类型检查 | vue-tsc && vite build 成功,零类型错误(P5-M1 清零保持) |
| 端到端 API | 独立后端 8011:POST /search/create 返回 batch_summary(1批,6点全pending) + l0_summary(sampled=6,pass_rate=1.0);GET /search/{id}/state 同样返回新字段 |
| 全量回归 | 16/16 PASS(含新增 test_search_state_summary) |
日期:2026-08-30 环境:Windows + 纯 stdlib(无 numpy/scipy/sklearn/lightgbm)
目的:完成 P5-M4 验收点"蓝图 §6 管线可运行;现有策略回归不破"——新增 Morris 灵敏度筛选策略 + 代理模型引导策略(含预算自适应批次大小),注册到 strategies 注册表。
MorrisStrategy(src/afmcore/strategies/morris.py,kind=morris)
state() 返回 sensitivity_ranking(每参数 mu/mu_star/sigma/n_effects,按 mu_star 降序)+ key_parameters(mu_star>0 的前半)SurrogateGuidedStrategy(src/afmcore/strategies/surrogate_guided.py,kind=surrogate_guided)
state() 返回 phase(initial/surrogate_guided/exhausted)、budget 用量、surrogate 诊断(n_train/loo_rmse/mean_uncertainty/last_batch_size)| 项目 | 结果 |
|---|---|
| Morris 单元测试 | 15/15 PASS(test_strategy_morris.py:轨迹点数/step0无changed_param/线性函数灵敏度排名/收敛/空参数/单轨迹/奇数n_levels/参数边界/未知id/缺失metric/failed排除/注册/state契约) |
| Surrogate 单元测试 | 17/17 PASS(test_strategy_surrogate.py:初始LHS/bowl收敛/maximize/空参数/budget耗尽/n_initial>budget/自适应批次边界/未知id/缺失metric/failed排除/注册/state契约/IDW预测/距离计算/归一化往返) |
| Morris 冒烟 | 线性函数 y=2a+0.5b,灵敏度排名 a(mu_star=2.0) > b(0.5),sigma=0(线性无交互)✅ |
| Surrogate 冒烟 | bowl 函数 y=(a-0.5)^2+(b-0.5)^2,budget=30,best y=0.007(理想 0.0),LOO RMSE=0.089 ✅ |
| 策略注册 | list_strategy_kinds() = [adaptive, full_factorial, lhs, morris, surrogate_guided] ✅ |
| 全量回归 | 19/19 PASS(含 2 个新测试) |
日期:2026-08-30 环境:Windows + 纯 stdlib(无 Ansys Maxwell / JMAG 真实安装)
目的:完成 P5-M5 验收点"get_adapter("maxwell") 可跑 mock/真实链路"——新增 MaxwellAdapter 和 JMAGAdapter,注册到适配器注册表,执行器 tool 参数动态选择适配器。
MaxwellAdapter(src/afmcore/adapters/maxwell.py,tool=maxwell)
JMAGAdapter(src/afmcore/adapters/jmag.py,tool=jmag)
scripts/task_executor.py MotorCADTaskExecutor._ensure_adapter():从硬编码 import afmcore.adapters.motorcad 改为根据 self.tool 动态 import(motorcad/maxwell/jmag),未知 tool 依赖预注册适配器。executor_config.json 的 tool 字段(P5-M2 已加)现在可选择 "motorcad"/"maxwell"/"jmag"。| 项目 | 结果 |
|---|---|
| 适配器注册 | registered_tools() 含 maxwell/jmag ✅ |
| Maxwell mock 全链路 | connect→load→set→run→extract→run_point,status=OK,tavg=2.10(airgap=1,magnet=5)✅ |
| JMAG mock 全链路 | 同上,tavg=2.17(系数不同,可区分工具)✅ |
| 工具区分 | 相同参数 maxwell tavg=2.10 ≠ jmag tavg=2.17 ✅ |
| set_parameter 回读校验 | 写入后回读一致 ✅ |
| 边界:空参数 | tavg=0.10(所有参数默认 0)✅ |
| 边界:未 connect 就 run | 抛 RuntimeError ✅ |
| 异常:mock=False | connect() 抛 RuntimeError(环境依赖标注)✅ |
| 异常:未知 tool | get_adapter 抛 KeyError ✅ |
| 执行器动态 import | tool=maxwell→adapter.tool_name="maxwell";tool=jmag→"jmag";未知 tool→KeyError ✅ |
| 单元测试 | test_adapters.py 22/22 PASS |
| 全量回归 | 20/20 PASS(含新测试) |
日期:2026-08-30 环境:Windows + 纯 stdlib(无真实 Motor-CAD 热求解运行)
目的:完成 P5-M6 验收点"热指标入库与报告展示"——metrics.py 扩项(热网络+结构指标,自动生效)、robust_motorcad 热求解开关、report_generator 按物理域分组模板化。
新增 10 个指标(均 required=False,不影响现有必需指标校验):
热网络指标(domain=thermal): | key | label | unit | direction | |---|---|---|---| | winding_hotspot_temp_c | Winding Hotspot Temp | C | lower | | magnet_temp_c | Magnet Temp | C | lower | | stator_temp_c | Stator Temp | C | lower | | bearing_temp_c | Bearing Temp | C | lower | | temp_rise_c | Temperature Rise | C | lower | | thermal_resistance_k_w | Thermal Resistance | K/W | lower |
结构/机械指标(domain=structural): | key | label | unit | direction | |---|---|---|---| | axial_force_n | Axial Force | N | lower | | radial_force_n | Radial Force | N | lower | | max_stress_mpa | Max Stress | MPa | lower | | deformation_mm | Max Deformation | mm | lower |
每个指标含英文+中文(\uXXXX)别名。extract_all_metrics() 遍历 METRIC_DEFINITIONS,新指标自动被提取,无需调用方修改。总指标数从 25 增至 35。
__init__ 新增 enable_thermal: bool = False(默认关,保持现有电磁-only 行为)run_single_point 新增 enable_thermal: Optional[bool] = None(覆盖实例默认)do_thermal_calculation()(失败记录警告,不中断电磁结果)_metric_display() 格式化 label(含 unit)和 value(float 用 %.4g)metrics_by_domain 字段| 项目 | 结果 |
|---|---|
| 新指标定义 | 热6+结构4,均有 domain 字段,required=False ✅ |
| 总指标数 | 35(原25+新10)✅ |
| 热指标提取 | mock CSV 含 Magnet Temperature 等字段,extract_all_metrics 自动提取 ✅ |
| 结构指标提取 | mock CSV 含 Axial Force 等字段,自动提取 ✅ |
| 中文别名 | \u6c38\u78c1\u4f53\u6e29\u5ea6 → magnet_temp_c ✅ |
| 必需指标校验 | 缺热/结构指标不影响 check_required_metrics ✅ |
| 域分组 | electromagnetic/thermal/structural 正确分组,空域跳过 ✅ |
| 未知 key | 默认归入 electromagnetic ✅ |
| 报告 JSON | metrics_by_domain 字段存在,热/结构域正确 ✅ |
| robust 热参数 | init 和 run_single_point 均有 enable_thermal 参数 ✅ |
| 单元测试 | test_metrics_extension.py 20/20 PASS |
| 全量回归 | 21/21 PASS(含新测试) |
修复 Plan 23 全部 80 个扫描点失败的问题,并建立根本性防护机制,防止 RFM/AFM 变量名不匹配错误再次发生。
Plan 23 的扫描变量使用了径向磁通电机(RFM)的变量名:
Stator_Lam_Outer_Dia(80~100mm,5 档)Stator_Lam_Inner_Dia(45~60mm,4 档)Magnet_Thickness(2~5mm,4 档)4 × 5 × 4 = 80 个点,全部在写入第一个参数 Stator_Lam_Outer_Dia 时失败:
RuntimeError: MotorCADError writing Stator_Lam_Outer_Dia:
pymotorcad: set_variable: Error in SetVariable: Could not find Stator_Lam_Outer_Dia
当前模型 MARS-12S10P_SSSR_D76-C150_V5.0-0819.mot 是轴向磁通电机(SSSR),正确的变量名是 Stator_Outer_Diameter / Stator_Inner_Diameter。
topology_variable_map.py:拓扑感知变量名映射表(41 个 AFM 已知变量 + RFM→AFM 别名映射 + 模板逻辑名映射)_expand_plan_to_parameters():扫描变量经过模板 motorcad_var + 拓扑别名映射start_simulation 执行前变量名校验:未知变量返回 400 + 建议名GET /api/plans/variable-catalog API| 测试项 | 结果 |
|---|---|
| 拓扑归一化(SSSR/AFIR/RFM/None/别名) | ✅ PASS |
| RFM→AFM 别名解析(Stator_Lam_Outer_Dia → Stator_Outer_Diameter) | ✅ PASS |
| 模板逻辑名映射(Number_of_Slots → Slot_Number) | ✅ PASS |
| 已知变量校验(AFM 变量已知,RFM 变量在 AFM 拓扑未知) | ✅ PASS |
| 参数批量校验(valid/unknown/aliases_resolved 分类) | ✅ PASS |
| 未知变量建议(suggest_alternative) | ✅ PASS |
| 已知变量集合获取(41 个 AFM 变量) | ✅ PASS |
| Plan 23 回归测试(80 点,RFM 名被映射,全部已知) | ✅ PASS |
scripts/test_topology_variable_map.pypython scripts/test_topology_variable_map.py在项目详情页点击"一键 AI 生成方案"按钮,前端报错。后端返回 422:
Invalid generated plan: plan_data malformed: could not convert string to float: 'Star'
src/plan_schema.py 中 FixedParam.value 被定义为 float 类型,且 from_dict() 中强制 float(d.get("value", 0.0)) 转换。
AI 生成的方案中包含字符串枚举类型参数:
Winding_Connection: "Star"(星形连接)Cooling_Type: "Natural Convection"(自然冷却)CurrentDefinition: "Peak"(峰值电流)这些是 Motor-CAD 合法的枚举/字符串参数,但 float("Star") 抛出 ValueError,被 validate_plan_dict() 捕获后返回 422。
修改 src/plan_schema.py:
FixedParam.value 类型从 float 改为 Any(支持数字和字符串枚举)from_dict() 中移除 float() 强制转换,保持原始值类型generate_full_params() 返回类型注解从 dict[str, float] 改为 dict[str, Any]| 测试项 | 结果 |
|---|---|
| FixedParam 接受字符串枚举值(Winding_Connection="Star") | ✅ PASS |
| 数字值(int/float)仍正常工作 | ✅ PASS |
| to_dict -> from_dict 字符串值往返保留 | ✅ PASS |
| 混合数字/字符串参数的方案校验通过 | ✅ PASS |
| generate_full_params 保留字符串枚举值 | ✅ PASS |
| 空 fixed_params 边界情况 | ✅ PASS |
| AI 生成方案完整回归测试(9 固定参数 + 2 扫描变量 = 9 点) | ✅ PASS |
scripts/test_plan_schema.pypython scripts/test_plan_schema.py日期:2026-09-01
测试环境:Windows,Python 3.14.7(AI shell),Motor-CAD v261,git 仓库
测试目的:验证新增的 scripts/check_machine_paths.py(Playbook V2 落地:换机/新会话环境体检)能正确检查并报告环境状态。
测试脚本:scripts/check_machine_paths.py
输出目录:无(只读体检,stdout 直接输出)
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | 运行 python scripts/check_machine_paths.py |
✅ | 退出码 1(存在缺项时按设计返回 1) |
| 2 | Python 版本 | ✅ | 3.14.7(≥3.10) |
| 3 | 环境变量 | ✅ | MOTORCAD_ACTIVEX=...activex.bat;ANSYSLMD_LICENSE_FILE=1055@localhost |
| 4 | Motor-CAD exe | ✅ | activex.bat + D:\Program Files\ANSYS Inc\v261\motorcad\MotorCAD.exe 均存在 |
| 5 | Python 依赖包 | ⚠️ | 6 包在当前 AI shell 解释器 MISSING(预期:shell 未装项目依赖,需在项目实际解释器下运行或 pip install) |
| 6 | Git 状态 | ⚠️ | HEAD 有效;工作区有未提交改动(本次框架升级文件,待提交) |
| 7 | 仓库资产 | ✅ | models/*.mot、experience.db、executor_config.json、web/、src/afmcore 全部就位 |
| 8 | node/npm | ✅ | 在 PATH 上 |
| 9 | py_compile + ASCII | ✅ | check_machine_paths.py 编译通过、纯 ASCII(符合硬性约束 §1) |
.venv/.env(venv 探测未命中)→ 包缺失反映的是当前 shell 解释器视图,非项目实际运行环境;项目真实依赖需按 KNOWLEDGE_BASE §1 安装(pip install ansys-motorcad-core pyside6 pandas 等)。find_spec 全部 MISSING 属环境差异而非脚本 bug。--fix 打印精确修复命令(setx / pip install)但不自动执行,避免脚本擅自改系统环境。日期:2026-09-02 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Kimi k3,SQLite 测试目的:验证 AI 一键生成方案在 topology='AFIR' 且 search_strategy.method='full_factorial_grid' 时不再 422 报错,正确归一化兜底。 相关文件:web/frontend/src/views/ProjectList.vue、web/backend/app/services/plan_generator.py、web/backend/app/routers/ai_plan.py
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile 语法检查 | ✅ | 两个改动 .py 编译通过 |
| 2 | afmcore.topology.is_supported | ✅ | AFIR=False,SSSR/DRSS/SDSR=True |
| 3 | afmcore.strategies 归一化 | ✅ | full_factorial_grid 未注册;active_learning→adaptive 已注册 |
| 4 | convert_ai_plan_to_unified 函数级测试 | ✅ | method=full_factorial_grid→full_factorial + warning;method=lhs 保留 |
| 5 | 真实端到端 API(AFIR 项目 id=9 generate-and-save) | ✅ | HTTP 200,topology→SSSR、method→full_factorial,warnings 正确 |
日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Kimi k3,Vue3 + Element Plus 测试目的:验证 P0-2(Kimi max_tokens 撞顶导致 content 空)与 P0-1(AI 生成摘要对话框)修复。 相关文件:web/backend/app/services/ai_client.py、web/backend/app/services/plan_generator.py、web/frontend/src/views/ProjectDetail.vue
max_tokens=2000(.env 的 KIMI_MAX_TOKENS=4096 未生效);k3 推理模型的 reasoning_content 会吃满 2000,导致 content 为空 → JSON 解析失败 → "AI 生成失败"(对应用户"超时"截图的一个隐藏根因,ai_call_logs id=40 实测 completion_tokens=2000、content 空)。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII 检查(2 个 .py) | ✅ | 编译通过、纯 ASCII |
| 2 | vue-tsc --noEmit 类型检查 | ✅ | 0 错误 |
| 3 | 端到端 generate-and-save(SSSR 项目 id=1) | ✅ | HTTP 200,topology=SSSR,warnings 完整返回 |
| 4 | max_tokens 生效核对(最新 ai_call_log id=45) | ✅ | completion_tokens=650(未撞顶)、content 完整 JSON、duration 18.5s、status=success |
日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Vue3 + Element Plus 测试目的:验证 P0-3(PlanDetail 仿真前检查清单)与 P0-4(TaskManager 创建任务从方案自动展开参数)。 相关文件:web/backend/app/routers/plans.py、web/backend/app/routers/tasks.py、web/frontend/src/views/PlanDetail.vue、web/frontend/src/views/TaskManager.vue
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII(plans.py/tasks.py) | ✅ | 编译通过、纯 ASCII(preflight 只返回 key/status,中文 label 在前端) |
| 2 | vue-tsc --noEmit | ✅ | 0 错误 |
| 3 | preflight API(plan 1)首次 | ⚠️→✅ | 初测 model_path fail(相对路径 models/xx.mot 相对后端 cwd 解析失败);修复为用 PROJECT_ROOT 解析相对路径后 pass |
| 4 | preflight API 复测 | ✅ | ok=true;model_path pass、scan_vars=1、point_count=3、executor warn(0 在线) |
| 5 | tasks 自动展开(POST /api/tasks 仅传 plan_id=1) | ✅ | HTTP 200,total_points=3(1 变量 × 3 值自动展开),status=pending |
GET /{plan_id}/preflight(5 项检查:模型文件/变量名确认/扫描变量/数据点规模/执行器在线;fail 阻断、warn 提示);model_path 相对路径用 PROJECT_ROOT 解析。POST /api/tasks 的 plan_data/parameters 改为可选;仅传 plan_id 时自动加载方案并调用 _expand_plan_to_parameters 展开,显传仍优先(高级覆盖)。7d55dc4f 已 cancel(任务文件在 output/tasks/,不入库)。日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Kimi k3 测试目的:验证 D6 数据一致性 Bug 修复——ProjectDetail 录入的边界条件 key(current_a/speed_rpm 等)能流入 build_default_fixed_params 的固定参数推断。 相关文件:web/backend/app/services/fixed_params_template.py
build_default_fixed_params 读取 BC key 用 rated_current_a/rated_speed_rpm/slot_count/dc_link_voltage_v/cooling_method,而 ProjectDetail 录入 + rule_engine 消费用 current_a/speed_rpm/slots/voltage_v/cooling_type → 用户在项目边界表单填的电流/转速/槽数/电压/冷却方式不流入固定参数推断(落模板默认值)。Magnet_Temperature/Max_Speed 完全无 BC 推断。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII | ✅ | 通过 |
| 2 | 函数级验证(11 断言) | ✅ | 前端 7 key 全部正确流入;旧 rated_ key 向后兼容;调用方 dict 不被修改 |
| 3 | 端到端(project 9 generate-and-save) | ✅ | HTTP 200;RMSCurrent=20(BC)、Shaft_Speed=3000(BC)、Number_of_Slots=12、DC_Link_Voltage=48、Magnet_Temperature=40、Cooling_Method=Natural、Max_Speed=6000,全部来自 BC 而非模板默认 |
日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Kimi k3,Vue3 测试目的:验证 BC 字段目录单一事实源落地——后端目录 API、方案保存 BC、PlanDetail BC 展示从目录渲染。 相关文件:web/backend/app/services/bc_fields.py(新建)、routers/generation.py、routers/ai_plan.py、routers/plans.py、web/frontend/src/views/PlanDetail.vue
GET /api/bc-fields 暴露目录。\uXXXX 转义直接落成实际中文字符 → 文件非 ASCII 且 docstring 字面 \uXXXX 触发 truncated escape。解决:先写中文,再用 encode('ascii','backslashreplace') 转换脚本统一转 \uXXXX;docstring 避免字面 \uXXXX。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII(5 个 .py) | ✅ | 通过、纯 ASCII |
| 2 | normalize_bc 功能 | ✅ | rated_current_a→current_a(规范优先)、slot_count→slots、cooling_method→cooling_type、unknown 透传 |
| 3 | vue-tsc --noEmit | ✅ | 0 错误 |
| 4 | /api/bc-fields | ✅ | 25 字段、label 中文正确、aliases 正确 |
| 5 | 端到端(project 9 generate-and-save) | ✅ | plan.boundary_conditions 完整保存 25 个规范 key 的 BC |
日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Kimi k3 测试目的:消除固定参数推断的双重转换——build_default_fixed_params 与 rule_engine 统一走 bc_fields.normalizebc 单一事实源,删除本地 rated 别名桥。 相关文件:web/backend/app/services/fixed_params_template.py、rule_engine.py、bc_fields.py
第一阶段后存在双重转换:normalizebc 输出 current 系,build_default_fixed_params 仍用本地 ALIASES 桥把 current 再转 rated_ 读取。本阶段统一为:BC → normalize_bc(唯一别名处理点)→ 各消费端直接读规范 key。
bc = normalize_bc(...),删除本地 _ALIASES 桥,elif 改读规范 key(current_a/speed_rpm/slots/voltage_v/cooling_type)。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII(3 个 .py) | ✅ | 通过 |
| 2 | 统一性验证(14 断言) | ✅ | current_ 规范 key 流入;rated_ 旧 key 经 normalize_bc 兼容;rule_engine 解析 rated_;不改调用方 dict |
| 3 | 后端运行时 import | ✅ | fixed_params_template→bc_fields、rule_engine→bc_fields 无循环,health OK |
| 4 | 端到端(project 9 generate-and-save) | ✅ | 固定参数推断仍全对(RMSCurrent=20/Shaft_Speed=3000/Slots=12/DC=48/MagnetTemp=40/Cooling=Natural/MaxSpeed=6000) |
日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Vue3 测试目的:验证 P2-1 耗时校准(实测 solve_time_s 替代硬编码)与 P2-3 AFIR 非标准拓扑前端标记。 相关文件:web/backend/app/routers/analytics.py、web/frontend/src/views/PlanDetail.vue、web/frontend/src/views/ProjectList.vue
GET /api/analytics/solve-time-stats(avg/min/max/median/count)。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII(analytics.py) | ✅ | 通过 |
| 2 | vue-tsc --noEmit | ✅ | 0 错误 |
| 3 | /api/analytics/solve-time-stats | ✅ | count=11, avg=125.9, min=118, max=141.4, median=121 |
| 4 | AFIR 项目识别 | ✅ | id 9/10/11 topology=AFIR 被识别为非标准,前端将标记 |
日期:2026-09-03 测试环境:Windows,系统 Python 3.12.10(uvicorn 0.52.4 / fastapi 0.141.1),Kimi k3 测试目的:解决 AI 推荐变量被误判"非标准"导致扫描维度被裁剪/警告的问题——扩充 SCAN_PARAMETERS 注册表 + 补变量名归一化映射。 相关文件:web/backend/app/services/rule_engine.py、plan_generator.py
AI 高频推荐但非标准的变量:Turns_per_Coil(匝数,9 次)、Stator_Outer_Diameter(定子外径,9 次)、Slot_Depth(3 次)、Stator_Inner_Diameter、Wire_Diameter。均为 fixed_params_template 里的有效 Motor-CAD 变量,仅因不在 SCAN_PARAMETERS(原 8 个)被误判。
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | py_compile + ASCII | ✅ | 通过 |
| 2 | 归一化验证(16 断言) | ✅ | 12 个变体名归一化到注册名;convert 不再产生"not a standard"warning;变量被保留 |
| 3 | 注册表扩充 | ✅ | 8→13,5 个新变量范围正确 |
| 4 | 端到端(project 9) | ✅ | "非标准变量"warning 消失;Stator_Outer_Diameter 保留为扫描维度(values=5) |
日期:2026-09-03 测试环境:Windows,Vue3 + Element Plus 2.4 测试目的:验证结果表列配置——默认只显示核心指标 + 扫描变量,35 项指标按需勾选显示(解决指标扩展后结果表全部铺开拥挤的问题 D14)。 相关文件:web/frontend/src/views/PlanDetail.vue
| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | vue-tsc --noEmit | ✅ | 0 错误 |
| 2 | 前后端服务 | ✅ | 前端 5173 HTTP 200,后端 health OK(纯前端改动,Vite 热更新) |
日期:2026-09-03 测试环境:Windows,Vue3 + Element Plus,系统 Edge headless(CDP 截图,Node 原生 WebSocket) 测试目的:用 ui-ux-pro-max 技能 + 实截图评审界面,修复发现的问题并截图回归验证。 方法:agent-browser 因 googleapis 下载 Chromium 超时,改用系统 Edge headless + 自写 CDP 截图脚本(output/_cdp_shot.mjs)实测 5 个页面。
| 项 | 问题(截图证据) | 修复 | 级别 |
|---|---|---|---|
| P0-1 | PlanDetail 概览"扫描变量数/预计数据点/预计耗时"全 0(读 plan.scan_variables 不存在,实为 plan_data.variables) | scanVariables 及增删改 4 处改读 plan_data.variables | Bug |
| P0-1b | calcPoints 只认 min/max/step,plan 1 variables 用 values 数组 → 预计数据点 0 | calcPoints 优先 values.length,兼容 min/max/step、start/stop | Bug |
| P1-1 | Dashboard 已选方案却提示"请选择方案";默认选第一个方案(常无结果);结果加载漏 .items 字段({total,items})致有结果显示 0 | 空状态文案区分已选/未选;默认选 result_count>0 方案;results 读取加 .items | Bug+交互 |
| P1-2 | ProjectDetail 边界条件 25 字段全铺开(22 个"未设置"占位) | 空值默认折叠,只显示已设置 + 展开全部 | 密度 |
| P1-3 | ProjectList 表格行高大 | 表格 size=small | 密度 |
| P2-2 | 面包屑 /plans/:id 缺项目名 | MainLayout 加载所属项目名,面包屑补"项目名"层级 | 导航 |
| P2-4 | ProjectDetail 标题区"返回"与项目名粘连 | 返回按钮独占一行 | 视觉 |
a?.items || a?.results || a?.data)。日期:2026-09-03 测试环境:Windows,Vue3 + Element Plus,系统 Edge headless(CDP 截图) 测试目的:结果表失败行显示具体错误原因,便于诊断仿真失败(此前 FAILED 状态无原因可查)。 相关文件:web/frontend/src/views/PlanDetail.vue、web/frontend/src/views/Dashboard.vue
RuntimeError: MotorCADError writing Outer_Rotor_Diameter: ... Could not find Outer_Rotor_Diameter),但结果表只显示 FAILED 状态,失败原因不可见。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | vue-tsc --noEmit | ✅ | 0 错误 |
| 2 | 截图 Dashboard(v_dashboard_err.png) | ✅ | 错误信息列直接显示 "Could not find Outer_Rotor_Diameter" 完整原因 |
日期:2026-09-03
测试环境:Windows,Motor-CAD 2026R1 (v261),pymotorcad 0.8.8,系统 Python 3.12.10,许可证 lmgrd+ansyslmd 在跑
测试目的:排查仿真失败根因(set_variable: Could not find Outer_Rotor_Diameter),实测确认 MARS 真实几何变量名并修正模板。
相关文件:web/backend/app/services/fixed_params_template.py、docs/KNOWLEDGE_BASE.md §3.3
Could not find Outer_Rotor_Diameter。.mot(INI 文本)静态比对模板变量名存在性。get_variable 实测候选名(独立隐藏实例,只读无求解)。set_variable + 回读校验修正后的变量名可写性(铁律"写入回读校验")。Outer_Rotor_Diameter→RotorOuterDiameter(130)、Stator_Outer_Diameter→Stator_Lam_Dia(76)、Stator_Inner_Diameter→Stator_Bore(50)、Rotor_Back_Iron_Thickness→Back_Iron_Thickness(5),get/set 均 OK。Inner_Rotor_Diameter(转子内径,4 候选全 MISS)、Stator_Yoke_Thickness(定子轭厚,3 候选全 MISS,PCB 无铁心)。Magnet_Arc_[ED]=121 实测 OK(原名即对,不改)。| 步骤 | 内容 | 结果 | 详情 |
|---|---|---|---|
| 1 | .mot 静态比对 | ✅ | 4 几何名 MISSING,别名映射多数 OK |
| 2 | get_variable 探测(22s) | ✅ | 22 个真实名 OK;模板 12 个错误名全 MISS;转子内径/轭厚候选全 MISS;MagnetArc[ED]=121 |
| 3 | set_variable + 回读(15s) | ✅ | 4 个修正名写入回读一致,ALL WRITABLE |
| 4 | py_compile + ASCII | ✅ | 模板编译通过、纯 ASCII |
motorcad_var=null 是"无对应变量"的安全处理(不写入不报错)。日期:2026-09-03 测试环境:Windows,Motor-CAD 2026R1 (v261),pymotorcad 0.8.8,许可证在跑 测试目的:模拟执行器完整流程(生成固定参数 → set 全部 → 真实求解 → 提取指标),端到端验证变量名修正后仿真能成功跑通。 相关文件:web/backend/app/services/fixed_params_template.py、docs/KNOWLEDGE_BASE.md §3.3
Current_Advance_Angle、Material_Stator_Lam_Yoke 也为错误名(几何 4 个已修正 OK)。Current_Advance_Angle→PhaseAdvance(get/set OK);Steel_Grade(Material_Stator_Lam_Yoke)不存在,MARS 无铁心 → 设 null。do_magnetic_calculation 失败——Could not find magnet material NdFeB_N42SH in solids database(材料值错误,非变量名)。.mot 实测 Material_Magnet=N42UH,模板默认 NdFeB_N42SH 改 N42UH。| 步骤 | 内容 | 结果 |
|---|---|---|
| set_variable(32 可写参数) | 全部 set | ✅ 32 ok, 0 failed |
| do_magnetic_calculation | 真实电磁求解 | ✅ 成功(~2 分钟,符合 90-150s) |
| export_results | 结果导出 | ✅ 337 行 CSV |
| 关键指标 | 求解结果有效性 | ✅ 转矩脉动 2.815%、AC 损耗 0.47W、功率因数 0.995 |
仿真失败根因(变量名 + 材料名)已彻底修复,端到端仿真能成功跑通并产生有效结果。模板所有 motorcad_var 经实测验证(无猜测)。
日期:2026-09-03 测试环境:Windows,Motor-CAD 2026R1 (v261),pymotorcad 0.8.8,FastAPI 后端 + 本地执行器(enable_mock=false) 测试目的:验证完整生产链路(非 pymotorcad 单点)在变量名修正后能成功跑通一次真实仿真。 相关文件:web/backend/app/services/topology_variable_map.py、scripts/task_executor.py、src/afmcore/adapters/motorcad.py
is_known_variable 用 _KNOWN_VARIABLES[SSSR](含错误几何名),把修正后的正确名误判 unknown。修复 1:topology_variable_map 的 _KNOWN_VARIABLES 几何名更正为 MARS 实测名(RotorOuterDiameter/Stator_Lam_Dia/Stator_Bore/Back_Iron_Thickness/PhaseAdvance),alias map 的 SSSR/AFIR 目标名同步更正。not claimable (claimed/network)——start-simulation 已把任务 pending→dispatched,执行器 claim 时再调 dispatch(后端仅允许 pending→dispatched),状态冲突被拒。修复 2:task_executor.execute_task 对 status==dispatched 的任务跳过重复 dispatch(仅 pending 才 claim)。No module named 'scripts'——afmcore.adapters.motorcad 用 from scripts.robust_motorcad import,执行器 sys.path 只有 scripts/ 和 src/(无仓库根)。修复 3:motorcad._ensure_solver 导入前确保仓库根在 sys.path。| 检查点 | 结果 |
|---|---|
| 预检(_KNOWN_VARIABLES) | ✅ 通过(修正后) |
| 执行器 claim(dispatched 任务) | ✅ 不再 "not claimable" |
| 适配器加载(scripts 导入) | ✅ 不再 "No module named 'scripts'" |
| 展开参数正确性 | ✅ RotorOuterDiameter=130/Stator_Lam_Dia=76/Stator_Bore=50/PhaseAdvance/N42UH 等全部正确 |
| 任务结果 | ✅ completed,successful_points=1,failed_points=0 |
| 关键指标 | ✅ tavg_nm=0.5219 Nm、efficiency=86.06%、total_losses=41.945 W(与 pymotorcad 单点验证一致) |
完整生产链路(Web 生成方案 → start-simulation 预检 → 任务下发 → 本地执行器真实 Motor-CAD 求解 → 结果回传 Web)全部通畅,变量名修正后仿真点成功。同时发现并修复了 3 个链路级问题(拓扑预检变量集、执行器 dispatch 状态机、适配器 scripts 导入路径)。
日期:2026-09-03
测试环境:Windows,Motor-CAD 2026R1,FastAPI 后端 + 本地执行器(enable_mock=false)
测试目的:多点扫描生产链路最终确认——批量调度、逐点落盘、进度更新、结果趋势物理正确性。
方案:plan 28(Airgap 0.6/1.0/1.5mm,3 点),task c2781acf。
| 检查点 | 结果 |
|---|---|
| 批量调度 | ✅ 执行器逐点跑,进度 33.3%→66.7%→100% |
| 任务结果 | ✅ completed,successful_points=3,failed_points=0 |
| 逐点落盘 | ✅ 每点结果独立保存(params + metrics + solve_time_s) |
| Airgap | tavg(Nm) | eff(%) | losses(W) | status |
|---|---|---|---|---|
| 0.6mm | 0.56625 | 84.926 | 49.917 | OK |
| 1.0mm | 0.52187 | 86.060 | 41.945 | OK |
| 1.5mm | 0.46770 | 86.346 | 36.558 | OK |
趋势符合电磁学:气隙↑ → 主磁通↓ → 转矩↓(0.566→0.522→0.468);气隙↑ → 铁耗/杂散损耗↓(49.9→41.9→36.6);损耗下降主导 → 效率略升(84.9→86.1→86.3)。结果真实有效,非随机数。
多点扫描生产链路完全通畅。单点耗时 ~134s(符合 90-150s 基线),3 点含 Motor-CAD 启动共约 6 分钟。从"仿真失败根因(变量名)"到"多点生产链路全通畅"彻底闭环。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 / Node 22.22.2 / FastAPI :8000 / Vite :5173 / Edge headless CDP 截图 |
| 测试目的 | 落地 UI 评审全部遗留项:PlanDetail 扫描变量编辑持久化、监控页合并、项目/任务批量清理、结果列配置 localStorage 持久化 |
/plans/{id} 完整 plan_data(后端单一事实源校验),保存后重载。✅ExecutionMonitor.vue,el-tabs 嵌入原 MonitorDashboard(任务监控)+ ExecutorMonitor(执行器状态),v-if 保证仅活动 tab 轮询。路由 /monitor 指向合并页,/executor-monitor 301 重定向兼容旧链接;导航"执行"组只留"任务管理/执行监控"两个入口。✅POST /api/projects/batch-delete(逐项容错)、DELETE /api/tasks/{id} + POST /api/tasks/batch-delete(仅终态可删,活动任务 400 拒绝并提示先取消)。localStorage['afm:plan-result-columns'](全局偏好),加载时读取,恢复默认时清除;空选择拦截"至少保留一列"。✅/monitor(单入口 + 双 Tab)、/tasks(多选列 + 行级删除)、/projects(多选列 + AFIR 警告标记 + small 密度)均符合预期。✅vue-tsc --noEmit 0 错误;3 个后端 .py 编译通过、纯 ASCII。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 / Node 22.22.2 / FastAPI :8000 / Vite :5173 / Edge headless CDP 截图(支持 js: 表达式点击) |
| 测试目的 | 用户实测反馈四需求:①拓扑基础模型自动调用(预检 model_path 空阻断启动)②新建项目弹窗全 25 项 BC + 来源标签 ③验收标准按 BC 自动带出 ④BC/固定参数默认全展开 + 可编辑保存 |
afmcore/topology.py 的 TopologyDefinition 加 default_model 字段(SSSR→MARS .mot,DRSS/SDSR 暂缺)+ default_model_for();三处回退——AI 生成(ai_plan.py)、手动创建(plans.py create_plan)、启动仿真运行时兜底(start-simulation 空则回填并持久化,16 个历史空模型方案无需手工修复直接可启动);preflight 模型失败项带 fixable/default_model。defaultBC() 原给全部 25 字段预填默认值 → 用户无法区分"自填/系统默认"。改为全空,仅保存非空字段(cleanBC)。bc_suggestions 输出(仅补用户未设置项)+ 扫描变量清单同步扩充至 13 项;方案存 bc_meta(user/ai 来源),手动创建全 user。plan.boundary_conditions/plan.acceptance_criteria 顶层不存在(实际在 plan_data 下)→ 兼容修正。"key <=110" → key <=110 字符串列表)。!== false)。.py 编译通过、纯 ASCII;vue-tsc 0 错误(初查报 2 个索引类型错误,修 defaultBC 返回类型标注后清零)。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 / FastAPI :8000 / Vite :5173 / Kimi k3 |
| 测试目的 | 验证 AI 补充 BC(bc_suggestions);三次生成均未被补充 → 深挖根因 |
ai_call_logs.prompt_preview 发现 system prompt 是 _default_prompt() 中文兜底版——真 prompt(generate.txt)从未被加载。web/backend/app/config.py 中 BACKEND_DIR = Path(__file__).parent = web/backend/app/,PROMPTS_DIR = BACKEND_DIR / "prompts" 指向不存在的 app/prompts/(实际在 web/backend/prompts/)→ prompt_path.exists() 为 False → 静默走 fallback。PROMPTS_DIR = BACKEND_DIR.parent / "prompts";附带修复:prompt 措辞改强制(REQUIRED FIELD)、ai_plan.py 项目上下文 BC 全量展开(未设置字段显式 null,模型才能看到哪些可补)、SCAN_PARAM_CN 补 4 个中文名。user:3 + ai:7,用户值未被覆盖。✅| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 |
| 测试目的 | 前次会话(P5-M2)未跟踪测试脚本 test_topology_variable_map.py 断言基于旧错误变量名(Stator_Outer_Diameter 等),在 TEST-036 修正后 6/8 失败;更新断言至 MARS 实测名并全量回归 |
test_plan_schema.py(plan_schema 字符串枚举支持):7/7 PASS,直接入库。✅test_topology_variable_map.py 初跑 2/8——失败断言正是旧错误名,证实 TEST-036 修正改变了行为。✅(预期失败)Stator_Outer_Diameter→Stator_Lam_Dia、Stator_Inner_Diameter→Stator_Bore、Outer_Rotor_Diameter→RotorOuterDiameter;新增"旧错误名应被判 unknown"反向断言(防回归);docstring 注明修正来源。✅src/plan_schema.py + style.css(P6-M1 设计令牌遗留)ASCII 检查通过并入库。✅前次会话(P5-M2/P6-M1)全部遗留改动已验证入库(commit 3dd42b9);测试断言与 MARS 实测变量名一致,旧错误名有反向防回归断言。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 / FastAPI :8000 / Kimi k3(真 prompt 首次生效) |
| 测试目的 | ①新 prompt 生成质量对比(变量名/验收标准格式)②补建 experience/extract.txt 并实测 |
| 维度 | 修复前(兜底 prompt) | 修复后(真 prompt) |
|---|---|---|
| 扫描变量名 | 编造名(OuterDia/Stator_Lam_Length)被裁剪 | 全注册标准名(Airgap/Magnet_Length/MagnetArc[ED]) |
| acceptance_criteria | 嵌套 dict(前端无法渲染) | 规范 list 判断式 4 条(efficiency_pct >= 90 等) |
| warnings | 多条裁剪/兜底警告 | 仅 model_path 回填提示 |
| bc_suggestions | 从不输出 | 正常输出(TEST-043 已证 7 项) |
prompts/experience/ 为空目录,experience_enhancer 一直走单行 fallback;且其 max_tokens=3000 有撞顶隐患(同步改为 KIMI_MAX_TOKENS)。smart-extract 端点为规则化提取(不走 AI);extract.txt 生效路径是 adaptive_loop 自适应闭环。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 / FastAPI :8000 / Kimi k3(真 prompt) |
| 测试目的 | 自适应闭环(adaptive_loop)端到端验证——extract.txt 真实生效路径 |
generate_plan 存 convert 后的 variables,initialize_search 读 scan_variables → "No valid scan variables"。修复:generate_plan 归一化补 scan_variables,initialize_search 双名兼容。start/stop/step,initialize_search 读 min_value/max_value → 参数全丢。修复:lo = var.get("min_value", var.get("start")) 兼容 + values 数组推导范围。default_model_for 回填。airgap_mm/outer_diameter_mm),闭环传 Motor-CAD 名(Airgap/Magnet_Length)→ L0 "No checks were performed" 全判不可行 → 初始 LHS 批次为空。需要 Motor-CAD 名 → L0 BC 名的语义映射层(注意 Magnet_Length(轴向) ≠ magnet_thickness_mm(径向厚度),映射不能瞎对应)。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / Python 3.12.10 / FastAPI :8000 / Kimi k3 / 本地执行器(真实 Motor-CAD) |
| 测试目的 | 闭环全链路:create → generate-plan → init-search → next-batch → 执行器真实仿真 → report-results → update-experience |
src/afmcore/l0/prescreening.py 加 MOTORCAD_TO_L0 语义映射(Airgap→airgap_mm、Magnet_Length→magnet_thickness_mm[轴向磁通磁钢厚度=轴向尺寸]、RMSCurrent→current_a、Magnet_Temperature→magnet_temp_c、Stator_Outer/Inner_Diameter→outer/inner_diameter_mm),evaluate 入口翻译且 L0 原生 key 优先。函数级验证:4 项检查全 PASS + 原生 key 优先。✅select_next_batch 从不消费 generate_initial_batch 的 pending 点 → 开头先返回 pending 批次。✅report_loop_results 函数无 @router.post 装饰器,结果回传端点不可达(P3-M5 遗留)。已补。✅best_objective_value 初始 inf → JSON 500。导出转 None。✅value > None TypeError。导入时 None 保持默认哨兵。✅(export/import 检查点机制顺带实测通过)points 不是 batch(查询时误读字段名导致误判为空)。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试目的 | 验证闭环 submit-batch(生产路径:闭环自动创建任务给执行器) |
f19ba592(12 点 pending 剩余全部);任务文件每点 33 键(30 固定 + 扫描 + point_id),无错误变量名(Inner_Rotor_Diameter/Steel_Grade 已排除)。执行器秒捡起跑。✅/tasks/{id}/results 上报,不识别 adaptive_batch 类型、不调闭环 /adaptive/loops/{id}/report-results。闭环拿不到结果需手动桥接。这是 P3-M5 设计但未实现段,需执行器加 loop 回传逻辑(或 Web 侧轮询桥接)。f19ba592(12 点)在跑,完成后可手动 report 进闭环做主动学习第二轮验证。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-03 |
| 测试环境 | Windows / FastAPI :8000 / Kimi k3 / 本地执行器(真实 Motor-CAD) |
| 测试目的 | submit-batch 生产路径全跑通 + 第二轮主动学习 + 经验提取数据完整性 |
f19ba592,~24 分钟真实仿真)——生产路径(闭环自动创建任务→执行器捡起跑)验证通过。adaptive_loop.report_results:all_results 条目合入点的输入 params(从 search.state.points 按 point_id 取)。experience_enhancer._condense_results:输入参数经 MOTORCAD_TO_L0(单一事实源)翻译成 BC 名再提取——否则闭环的 Motor-CAD 名输入不会被提取。函数级验证:Airgap→airgap_mm、RMSCurrent→current_a 翻译提取 PASS。
两个数据完整性修复影响未来闭环(当前 loop 的 12 点旧条目已无参数,无法补救);函数级验证通过,端到端效果待下次闭环运行确认。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 闭合 TEST-047 发现的"执行器跑完不调闭环 report-results"缺口 |
scripts/task_executor.py 加 _report_to_adaptive_loop:execute_task 完成后,若 task_type == "adaptive_batch" 且有 loop_id,把每点结果映射为 {point_id, metrics, status} POST 到 /api/adaptive/loops/{loop_id}/report-results。best-effort(回传失败不影响任务本身的 results 上报)。_report_to_adaptive_loop → 闭环 n_results 0→3。✅链路级验证(回传调用 + 闭环接收),用合成 metrics 测连通性;仿真段真实性已由 TEST-046/048 的真实 Motor-CAD 运行证明。全闭环自动流转(submit-batch→执行器→自动回传→下一批)的端到端长时运行未做(需真实仿真数十分钟),建议生产使用中观察。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | ①search 服务(前端自适应优化页后端)在 L0 修复后出点验证 ②修复结果表转矩/脉动列空缺 |
POST /api/search/create(Airgap 0.6-1.5)→ initial_points 4、pending 4、infeasible 0(L0 修复前全判 infeasible)。前端自适应优化页后端链路健康。✅average_torque_nm/torque_ripple_pct,而指标单一事实源(afmcore/metrics.py)用 tavg_nm/ripple_pct。修复:PlanDetail/Dashboard 列定义对齐事实源 + 平铺时旧名别名兼容(老数据 average_torque_nm → tavg_nm)。截图验证:转矩/脉动列正常显示(0.566/5.45 等),趋势符合物理。✅| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 验证闭环 AI 提取的经验真正沉淀到经验库(可被后续 AI 生成复用) |
generate_experience_entry 只返回 dict(注释自称 "ready for database storage"),update_experience 只在 HTTP 响应里返回、从不入库——重启即失,经验库页看不到,后续 AI 生成(读经验库 existing_experience)无法复用。闭环价值断裂。adaptive_loop.update_experience 加 _persist_experience_case:把 AI 洞察映射为 ExperienceCase 入库——best feasible point 的 params/metrics + summary+design_rules 作 conclusion + tags(topology/ai-insights/loop)。best-effort(入库失败不中断闭环),返回 experience_case_id。f19ba592)+ update-experience → experience_case_id: 7,experience_cases 表 6→7 行,结论为 AI 洞察文本,tags 含 ai-insights。✅/api/experience 列表可见 case 7(经验库页可读)。✅| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 验证"后续 AI 生成复用经验库"的真实性(上次口头声明未验证) |
ai_plan.py 的 generate-and-save(用户实际用的"AI 一键生成")调 generator.generate() 时不传 existing_experience;/generate 端点也只在请求体显式传了才用;前端两个生成入口都不传。→ 经验库的值根本没流入 AI 生成,闭环提取的经验入库了但生成时不读,价值链在"复用"环节断裂。_load_experience_cases(db, topology):按拓扑从 experience_cases 加载最近 5 条(params/metrics/conclusion/tags)。_load_experience_cases 直接调用返回 5 案例(含闭环 case 7 的 AI 洞察)。✅| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试环境 | Windows / FastAPI :8000 / Kimi k3 / 本地执行器(真实 Motor-CAD) |
| 测试目的 | 修复批次语义(submit 全部 pending 问题)+ 真实全自动闭环验证 |
初始 pending 4 → batch1 选 2 标 dispatched → pending 减到 2(不重复)→ submit 目标正好 2(修复前是全部)。✅
P3-M5 自适应闭环至此真正全自动:submit-batch→执行器真实仿真→自动回传→AI 分析→经验入库→后续生成复用,全程无手动桥接。这是本项目"AI 驱动智能仿真闭环"的完整实证。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 修复执行器架构弱点:心跳与任务执行同线程串行,长跑任务期间心跳停止被误判 offline |
poll_loop 单线程串行:_send_heartbeat() 与 execute_task() 同线程。Motor-CAD 单点求解约 2 分钟,跑点期间心跳完全停止 → 后端按 last_heartbeat 超时误判执行器 offline。本轮实测中执行器 30216 出现"进程活着但 offline"假死。start_polling 拆为两个线程:独立 heartbeat_loop(每 interval 秒心跳)+ poll_loop(取任务执行)。任务执行期间心跳持续。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试环境 | Edge headless CDP(截图 + 控制台/异常捕获) |
| 测试目的 | /generate 端点回归 + 全前端路由健康走查 |
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 闭环后端已全自动实测通畅但无 UI 入口,新建前端页面 |
views/ai/AdaptiveLoop.vue:创建闭环表单(需求/总预算/批次大小)+ 闭环列表 + 详情(阶段状态卡、方案摘要、预算进度条、批次历史表、经验提取区)。adaptiveApi.submitBatch(api/ai.ts 缺失)。/ai/adaptive-loop + 导航"AI 智能"组加入口 + 面包屑映射。| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 修复 AI 调用日志截断导致的可观测性缺陷 + 实证经验案例进入 AI prompt(TEST-052 遗留验证缺口) |
ai_client._log_call 存 json.dumps(messages[:3])[:500]——500 字符截断在 system prompt 开头,user message(含项目 BC + 经验案例)完全不可见。TEST-043/052 两次因此无法从日志确认 AI 实际收到的内容。messages[:3] → messages(全部),[:500] → [:8000];response_preview [:1000] → [:2000]。AI 调用的输入完全可观测,后续调试 prompt 行为(变量名、BC 补充、经验复用)可直接查日志,不再黑盒。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 实测闭环页"一键自动运行"状态机(TEST-056 遗留:UI 串接未实机跑过) |
api/ai.ts:adaptiveApi 的 generatePlan / reportResults / updateExperience 补 { timeout: 180000 }。AdaptiveLoop.vue startAutoRun 改为断点续跑:进入时先刷新 phase,init 才生成方案,plan_generated 才初始化搜索,search_initialized 及以后直接进批次循环。任何中断后重点"一键自动运行"即可从断点继续。闭环"一键自动运行"从 UI 点击到经验入库的全链路首次端到端实测通过。TEST-056 的验证边界闭合。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | dev 服务器正常≠生产构建能过;git status 巡检发现共享组件未跟踪 |
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试环境 | Motor-CAD 2026R1 (v261),pymotorcad(motorcad2maxwell/.venv),MARS 模型,1055@localhost 许可证可达 |
| 测试目的 | 首次真实验证 Motor-CAD 热仿真(此前 HANDOFF 标注"热求解待真实验证") |
P5-M6 引入的 enable_thermal 开关使用了两个不存在的 API,从未真正跑通:
mc.do_thermal_calculation() —— pymotorcad 无此方法(真实为 do_steady_state_analysis)mc.export_results("Thermal", ...) —— solution_type 无 "Thermal"(真实为 "SteadyState")| 步骤 | 耗时 | 结果 |
|---|---|---|
| 电磁计算 do_magnetic_calculation | 127.8s | 正常,损耗作为热源 |
| 稳态热 do_steady_state_analysis | 6.0s | 正常 |
| 导出 export_results("SteadyState") | — | 9 个 section 完整 |
热指标实测值:
| 指标 | 值 | 说明 |
|---|---|---|
| winding_temp_c 绕组平均 | 67.95°C | T [Winding (A) Average] |
| winding_hotspot_temp_c 绕组热点 | 74.59°C | T[绕组最高] = EWdg Outer Max |
| magnet_temp_c 磁钢 active | 118.15°C | 磁钢最高温,热风险首要关注 |
| stator_temp_c 定子轭 | 55.49°C | T[定子轭] |
| bearing_temp_c 后轴承 | 88.47°C | 前轴承仅 49.19°C,后轴承是热风险点 |
| temp_rise_c 温升 | -56.88°C | ⚠ 负值,见下 |
| thermal_resistance_k_w 热阻 | -11.07 K/W | ⚠ 负值,见下 |
[Miscellaneous] 中 Ambient_Temperature=125(环境 125°C,
而辐射环境 T_Ambient_Radiation=40 正常),导致温升/热阻为负值。
待用户确认后修正为 25~40°C。scripts/robust_motorcad.py:do_thermal_calculation() → do_steady_state_analysis();
export_results("Thermal") → export_results("SteadyState")。src/afmcore/metrics.py:7 个热指标补充实测字段别名(中英文),bearing_temp_c 映射到后轴承。scripts/run_thermal.py:独立热仿真验证脚本(可复用)。scripts/test_metrics_extension.py 20 项全部通过(含热指标、enable_thermal 签名)。extract_all_metrics 提取 7 项热指标全部命中。热仿真链路首次真实跑通,API 与字段名已核实登记。剩余阻塞:模型环境温度异常待确认。
| 项 | 分离式(先电磁后热) | 磁热耦合 do_magnetic_thermal_calculation |
|---|---|---|
| 耗时 | 134s | 474.2s(~3.5×) |
| 磁钢 active | 118.15°C | 110.68°C |
| 绕组热点 | 74.59°C | 76.43°C |
| 平均转矩 | 0.566 Nm | 0.515 Nm |
| 转矩脉动 | 5.45% | 2.78% |
| 总损耗 | 49.92W | 42.57W |
结论:磁热耦合更准确(温度反馈迭代)但更慢。"省时间"选分离式(enable_thermal 已实现)。
| 项目 | 内容 |
|---|---|
| 测试日期 | 2026-09-04 |
| 测试目的 | 验证执行器 enable_thermal 全链路(RobustMotorCADSolver→热求解→热指标落盘 CSV),此前仅代码透传 + 单元测试 |
RobustMotorCADSolver(enable_thermal=True) 跑单点:电磁 + 稳态热求解均成功(status=OK)。scan_results.csv(header 含全部热指标列)。执行器 enable_thermal 链路端到端 PASS。热仿真已完整接入生产链路(配置开关 → adapter → solver → 热指标落盘)。
ambient_temperature 已固化到执行器配置(默认 25°C,executor_config.json + EXECUTOR_AMBIENT env 可调),
RobustMotorCADSolver(enable_thermal=True, ambient_temperature=25.0) 构造参数方式复测端到端 PASS
(温升 +27.57、热阻 +5.657,与 params 传参方式结果一致)。