268 lines
20 KiB
Markdown
268 lines
20 KiB
Markdown
# StandardScene 架构重构方案
|
||||
|
|
|
|||
|
|
> 配套文档:《StandardScene代码审查报告.md》(质量/缺陷)、《StandardScene拆分计划.md》(拆分进度)
|
|||
|
|
> 本文聚焦**结构与架构合理性**:现状全景 → 逐模块深度分析 → 目标分层 → 程序集边界 → net8.0 去 Windows → 分阶段迁移路径。
|
|||
|
|
> 日期:2026-06-09
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 一、现状架构全景
|
|||
|
|
|
|||
|
|
### 1.1 程序集与依赖
|
|||
|
|
|
|||
|
|
| 程序集 | AssemblyName | TFM | 角色 | 依赖 |
|
|||
|
|
|---|---|---|---|---|
|
|||
|
|
| StandardScene.Core | `StandardScene` | net8.0-windows | 基座:抽象+业务+任务+调度+WebApi+UI | SimpleLite/SimpleCore/CommonUsage/MDCSToolBox/Topaz + NuGet(MQTTnet/Nancy/Jint/EasyModbus/IoTClient/OpenXml/Newtonsoft) |
|
|||
|
|
| StandardScene.Devices | `StandardScene.Devices` | net8.0-windows | 具体设备驱动(门/充电桩/按钮盒) | →Core + SimpleLite/SimpleCore/Topaz + leegKeys-sdk |
|
|||
|
|
| StandardScene.Protocol.VDA5050 | `StandardScene.Protocol.VDA5050` | net8.0-windows | VDA5050 协议车型 | →Core + SimpleLite/SimpleCore + NuGet(MQTTnet/Nancy/Jint/Newtonsoft) |
|
|||
|
|
|
|||
|
|
插件清单 `scene.json`(Devices / VDA5050 各一份):
|
|||
|
|
|
|||
|
|
```json
|
|||
|
|
{ "id":"devices", "assembly":"StandardScene.Devices.dll", "requiresCore":"StandardScene.dll",
|
|||
|
|
"provides": { "doorControllers":[...], "chargeStations":[...], "buttonBoxes":[...] } }
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
发现机制:`SimpleLite.Utils.UiTypeDiscovery.AllTypes()` 跨程序集扫描 + 类型特性(`[DoorType]`/`[ChargeType]`/`[ButtonBox...]`/`[CarType]`)。
|
|||
|
|
|
|||
|
|
### 1.2 当前依赖方向(问题版)
|
|||
|
|
|
|||
|
|
```mermaid
|
|||
|
|
graph TD
|
|||
|
|
Devices --> Core
|
|||
|
|
VDA5050 --> Core
|
|||
|
|
Core -->|NuGet| MQTTnet
|
|||
|
|
Core -->|NuGet| Nancy
|
|||
|
|
Core -->|NuGet| EasyModbus
|
|||
|
|
Core -->|NuGet| IoTClient
|
|||
|
|
Core -->|NuGet| OpenXml
|
|||
|
|
Core --> WinForms[WinForms 12+ 窗体]
|
|||
|
|
Core --> SimpleLite
|
|||
|
|
subgraph 卫星
|
|||
|
|
Devices
|
|||
|
|
VDA5050
|
|||
|
|
end
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
**核心结构问题**:Core 是"万能基座"——既是抽象基座,又塞满了具体协议依赖(MQTT 属 VDA5050、Modbus/IoTClient 属设备、Nancy 属 WebApi、OpenXml 属报表),还内置 12+ WinForms 窗体。卫星只能依赖这个臃肿 Core,无法独立演进。
|
|||
|
|
|
|||
|
|
### 1.3 体量分布(非 Designer,前列)
|
|||
|
|
|
|||
|
|
WebApi 2686 / AbstractLoopMission 1858 / VehicleMonitor 1502(UI) / AbstractChainedDeliveryMission 1407(已 Compile Remove) / ChainedDeliveryMission 1365 / ChargeStationManagementForm 1250(UI) / AbstractChargeLogicMission 1143 / VDA5050Car 938 / DoorMission 932 / ButtonBoxManager 913 / DoorManager 848 / Kiva 827 / ButtonMission 743 / StandardChargeMission 671 / Commons 653 …
|
|||
|
|
|
|||
|
|
> 12+ 个 600~2700 行巨类,是可维护性的主要矛盾。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 二、结构性问题诊断(按影响排序)
|
|||
|
|
|
|||
|
|
| # | 问题 | 证据 | 影响 |
|
|||
|
|
|---|---|---|---|
|
|||
|
|
| S1 | **分层污染**:Core 背负协议/设备/报表专有依赖 | Core.csproj 引 MQTTnet/EasyModbus/IoTClient/Nancy/OpenXml | 卫星无法瘦身;Core 编译/部署重;职责不清 |
|
|||
|
|
| S2 | **WinForms 全模块渗透**,阻塞纯 net8.0 | 12+ `*.Designer.cs`(Charge 4 个 Form、VehicleMonitor、各 Manager/Viewer);三 csproj 均 `UseWindowsForms=true` + `net8.0-windows` | 无法 `net8.0` 跨平台/瘦运行;与"UI 迁 migu"目标冲突 |
|
|||
|
|
| S3 | **God-class 泛滥** | WebApi 2686 / AbstractLoopMission 1858 / ChainedDeliveryMission 1365 / AbstractChargeLogicMission 1143 … | 改动风险高、测试困难、并发态难推理 |
|
|||
|
|
| S4 | **充电子系统未独立**,却已自成体系(20 文件) | `Charge/` 任务+站点+配置+数据服务+通信+4 表单 | 应为独立卫星,却深埋 Core |
|
|||
|
|
| S5 | **抽象与实现同居 Core** | 设备基类/特性/Mission/Manager 在 Core,仅具体驱动在 Devices | 卫星仍强依赖 Core 内部;热插拔受限 |
|
|||
|
|
| S6 | **干净抽象反向耦合到巨类** | `Loop/ILoopRules.cs` 顶部 `using static AbstractLoopMission;`(依赖其嵌套 `LoopPoint`) | 好接口被巨类绑架,无法独立复用 |
|
|||
|
|
| S7 | **全局可变静态** | `DeliveryCallbackRegistry`(static 字典)、`Commons` 静态工具、各 `static HttpClient` | 隐式耦合、测试隔离难、生命周期不可控 |
|
|||
|
|
| S8 | **内核 Coder 注册表限定本程序集反射** | `ProgramCoderSet`/`SegmentPlan.Coder` 特性驱动、按内核程序集反射 | 导航类卫星(磁/二维码/激光)无法热插拔(C2 阻塞) |
|
|||
|
|
| S9 | **构建可移植性差** | csproj 多处绝对 `HintPath`(E:\Work…、D:\MDCS…) | 换机/CI 无法直接构建 |
|
|||
|
|
| S10 | **死文件/弃用并存** | `AbstractChainedDeliveryMission.cs`(1407) 被 `Compile Remove` 仍在树 | 认知噪音、误改风险 |
|
|||
|
|
| S11 | **命名空间与程序集名不一致** | 三程序集 `RootNamespace=StandardScene`;类型散落 `StandardScene.*` 子命名空间 | 物理边界与逻辑边界错位,难判断"谁属于谁" |
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 三、逐模块深度分析
|
|||
|
|
|
|||
|
|
> 每个模块:**职责 / 结构 / 依赖与耦合 / 主要问题 / 目标处置**。
|
|||
|
|
|
|||
|
|
### M1 CarTypes(车型族,11 文件)
|
|||
|
|
- **职责**:定义各 AGV 车型(Kiva 827、Forklift 398、MultiWheel*、MultiVehicle、DualLifting、ArmCar、DummyCar 666)+ 字段袋 `BasicFields`(50) + 车辆监控 UI `VehicleMonitor`(1502, WinForms)。
|
|||
|
|
- **结构**:字段袋 `BasicCarFields/SiteFields/TrackFields/PlanFields` 设计合理(`-1` 哨兵语义被 Coder 正确利用);车型类承载通信(HttpClient)、状态机、调度、UI、强制控制等多职责。
|
|||
|
|
- **耦合**:车型直引 `Commons`、HttpClient、`MessageBox`、内核类型;`VehicleMonitor` 把 UI 与车辆模型绑定。
|
|||
|
|
- **问题**:巨类(Kiva 827)、`async void`+`throw`(Kiva.ForceStop 619/659)、空 catch、硬编码 IP(192.168.2.1:8008)。
|
|||
|
|
- **目标处置**:车型保留在领域层;剥离"通信/HTTP/UI"为协作者(`ICarTransport`/`ICarStatusView`);`VehicleMonitor` 进 UI 程序集。
|
|||
|
|
|
|||
|
|
### M2 Coders(轨迹编码器,1 文件 + 车型内联)
|
|||
|
|
- **职责**:`CommonTrackCoders` 通用 `ITrackCoder`(磁导航统一 `MagneticTrackCoder`、避障 `AvoidanceParamCoder`4参/`AvoidanceParamLWCoder`2参)。
|
|||
|
|
- **结构**:本轮已去重、结构清晰;`CommonTemplateTrackCoder` 提供 `SiteFieldsType` 扩展点。
|
|||
|
|
- **耦合**:受内核 `ProgramTrackCoderSettings`/`TemplateTrackCoderSettings` 特性约束(S8)。
|
|||
|
|
- **目标处置**:继续把车型内联 Coder 收敛至此;待内核放开注册表后,导航类 Coder 可下沉到导航卫星。
|
|||
|
|
|
|||
|
|
### M3 Chained(链式/循环任务族,12+2 文件)
|
|||
|
|
- **职责**:`AbstractLoopMission`(1858)、`ChainedDeliveryMission`(1365)、`TransportMission`(549)、`LoopMission`、回调注册表/附着器、`Loop/` 规则接口、若干 Viewer(UI)。
|
|||
|
|
- **结构**:**两面性**——`Loop/ILoopRules`(IEnter/IExit/IJoin/IBranch/ITaskStrategy) 与 `DeliveryCallbackRegistry` 是规范的策略/注册表模式(亮点);但 `AbstractLoopMission` 是 1858 行巨类,且接口 `using static AbstractLoopMission`(S6)反向耦合其嵌套类型。
|
|||
|
|
- **耦合**:裸 `new Thread`+`while`+`Thread.Sleep`(P0-1 已改协作式停止);UI Viewer 混入。
|
|||
|
|
- **问题**:巨类、状态用字符串 `status.status`、`AbstractChainedDeliveryMission`(1407) 死文件(S10)。
|
|||
|
|
- **目标处置**:把 `LoopPoint/LoopTask` 等领域模型从巨类**上提**到 Model/Abstractions,让 `Loop` 接口独立;巨类按"调度循环/任务编排/显示"拆分;删除/归档死文件。
|
|||
|
|
|
|||
|
|
### M4 InterLock(互锁,4 文件)
|
|||
|
|
- **职责**:`AbstractInterlockMission`(367)、`TrafficInterlockMission`、Viewer(UI)。交通互锁逻辑。
|
|||
|
|
- **耦合**:与调度/交通控制耦合;含 Viewer。
|
|||
|
|
- **目标处置**:归入"交通/调度"领域子模块;UI 外提。
|
|||
|
|
|
|||
|
|
### M5 Scheduler(调度后台任务,4 文件)
|
|||
|
|
- **职责**:`HeartBeatMission`、`NodeIsEnableMission`、`SecuritySignalMission`、`RegionalTrafficControlMission`(377)。周期性后台任务(心跳/站点禁用/安全信号上传/区域交通)。
|
|||
|
|
- **耦合**:直发 HTTP(硬编码端点)、`Console.WriteLine`、原 `while(true)`+`Thread.Abort`(P0-1 已修为 `while(started)`/协作式)。
|
|||
|
|
- **问题**:每个任务各写一套线程循环(重复),无统一基类。
|
|||
|
|
- **目标处置**:抽 `MissionRunnerBase`(CancellationToken + 状态枚举 + 统一日志),所有周期任务复用。
|
|||
|
|
|
|||
|
|
### M6 Charge(充电子系统,20 文件 + ChargeStationType)★需独立
|
|||
|
|
- **职责**:任务(`StandardChargeMission`671/`AbstractChargeLogicMission`1143)、站点(`AbstractChargeStation`/`ChargeStation`)、配置(`ChargeStrategyConfig`/`AlarmConfig`/`ChargingSetting`)、数据服务(3 个 *DataService)、通信(`ChargeUdpService`/`CommunicationMessage(Service)`)、Helper、**4 个 WinForms 表单**。
|
|||
|
|
- **结构**:自成完整子系统(任务+设备+配置+持久化+通信+UI),但全埋 Core。`CommunicationMessageService` 是**安全解析范本**(先校验长度)。
|
|||
|
|
- **耦合**:与具体充电桩驱动(Devices/Charge)双向(Core 持任务/抽象,Devices 持 PCB/FL/MuXing 驱动);实时 UDP 路径越界(P0-3 已修)。
|
|||
|
|
- **目标处置**:升级为**独立卫星 `StandardScene.Charge`**(含 Mission/抽象/配置/通信),具体桩驱动留 `Devices` 或并入;4 表单进 UI 程序集;通过 Abstractions 与 Core 解耦。
|
|||
|
|
|
|||
|
|
### M7 ExtendDevice + Devices(设备:门/按钮盒,Core 侧 13 + Devices 侧 6)
|
|||
|
|
- **职责**:Core 侧 = 基类(`BasicDoorController`/`BasicButtonBox`)+特性(`DoorTypeAttribute` 等)+管理器(`DoorManager`848/`ButtonBoxManager`913, 含 UI)+任务(`DoorMission`932/`ButtonMission`743)+模型/Monitor(UI);Devices 侧 = 具体驱动(`ModbusDoorController`/`Azowie`/`Leeg`/3 充电桩)。
|
|||
|
|
- **结构**:**新驱动质量优秀**(`ModbusDoorController`:CTS 协作停止/锁/变更检测/重连节流/统一日志);`DoorTypeAttribute` 特性发现规范。
|
|||
|
|
- **耦合**:抽象+业务在 Core、驱动在 Devices(S5);Manager 含 WinForms。
|
|||
|
|
- **问题**:`ModbusDoorController` 用析构函数兜底 `Disconnect`(GC 线程取锁+Wait,风险)→应实现 `IDisposable`;Manager 巨类含 UI。
|
|||
|
|
- **目标处置**:把设备**抽象+特性**下沉到 `StandardScene.Abstractions`;Manager 拆"设备生命周期服务 + UI";驱动统一 `IDisposable`。
|
|||
|
|
|
|||
|
|
### M8 Protocol.VDA5050(协议卫星,9 文件)
|
|||
|
|
- **职责**:`VDA5050Car`(938)、`MasterMQTTCommunication`、`VDA5050Interface/Segment/Helper/Commons`、`VDA5050WebApi`、`TextViewer`(UI)。
|
|||
|
|
- **结构**:已是独立卫星(好);自带 WebApi 与 MQTT 栈。
|
|||
|
|
- **问题**:`async void`+`throw ex`(240)、硬编码 `192.168.2.1:8008` 且注释掉按车地址(150)、空 catch、`Console.WriteLine` 满布、`monitor()` 死局部函数。
|
|||
|
|
- **目标处置**:作为协议卫星范本;端点配置化(按车 `address`)、异步规范化、日志统一、`VDA5050WebApi` 与 Core WebApi 走统一 `ApiResult`/路由约定。
|
|||
|
|
|
|||
|
|
### M9 WebApi(老 Nancy 接口,2686 行)★最高优先重构
|
|||
|
|
- **职责**:车辆/任务/地图/配置等 HTTP 接口(Nancy 2.0)。
|
|||
|
|
- **结构**:单文件上帝路由;错误响应 `new{Success=false,Code=500,...}` 复制几十处;反射 execute 端点(P0-2 已加白名单)。
|
|||
|
|
- **目标处置**:抽 `ApiResult.Ok/Fail` + 按资源拆模块(CarApi/MissionApi/MapApi…);统一鉴权中间件(来源/令牌,配置驱动);老接口归 `WebApi.Core(deprecated)` 规划迁移;最终独立 `StandardScene.WebApi` 程序集(隔离 Nancy 依赖)。
|
|||
|
|
|
|||
|
|
### M10 Model(领域/配置模型,12 文件)
|
|||
|
|
- **职责**:`Map/SimpleMap/MapStructure`、`SimpleConfig`、`TaskModel/LoopTask/MissionState`、`VehicleStatus`、各 `*Setting`。
|
|||
|
|
- **结构**:领域模型与配置混居;`Map.cs` 含硬编码 `127.0.0.1:4321`。
|
|||
|
|
- **目标处置**:拆"纯领域模型(→Abstractions)"与"配置(→Configuration)";端点配置化。
|
|||
|
|
|
|||
|
|
### M11 基础设施(TCP 5 / Utils 4 / CommonTools 2)
|
|||
|
|
- **职责**:`AsyncTcpClient`(432, 质量较好)+事件args;`JsonParser/JsonTool/ModbusClass/WebAPIHelper`;`AtomicFileUpdateHelper/SnowflakeIdGenerator`。
|
|||
|
|
- **问题**:`AsyncTcpClient.Send` 抛 `InvalidProgramException`(类型不当)、`EndWrite` 无异常处理、`uint on` 未用;`ModbusClass` 与设备 Modbus 重复关注点。
|
|||
|
|
- **目标处置**:归入 `StandardScene.Infrastructure`(net8.0 纯净,无 Windows);TCP/IO/序列化/ID 通用化。
|
|||
|
|
|
|||
|
|
### M12 Core 根 God-files(Commons 653 / Heuristic / LadderLogic / StandardCADTool / WebApi)
|
|||
|
|
- **职责**:`Commons` 万能工具+调度(`NearestTask`)、`Heuristic` 启发式、`LadderLogic` 梯形逻辑、`StandardCADTool` CAD(硬编码盘符路径、`async void`)。
|
|||
|
|
- **问题**:`Commons.AddOrUpdateXxxField` 重复 4 份、`CarValue` 忽略 key、`GoSite` 假重试(详见审查报告 P2-1);根目录堆放无归属大文件。
|
|||
|
|
- **目标处置**:`Commons` 按职责拆(字段服务/调度服务/控制台辅助);`StandardCADTool` 路径配置化、归 CAD 子模块。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 四、目标架构
|
|||
|
|
|
|||
|
|
### 4.1 分层与程序集边界(目标)
|
|||
|
|
|
|||
|
|
```mermaid
|
|||
|
|
graph TD
|
|||
|
|
subgraph L0[抽象层 net8.0 纯净]
|
|||
|
|
Abstractions[StandardScene.Abstractions<br/>接口/特性/字段袋/领域模型/ITrackCoder/设备契约]
|
|||
|
|
Infra[StandardScene.Infrastructure<br/>TCP/序列化/ID/IO/ILogger]
|
|||
|
|
Config[StandardScene.Configuration<br/>配置模型+读写]
|
|||
|
|
end
|
|||
|
|
subgraph L1[领域层 net8.0]
|
|||
|
|
Core2[StandardScene.Core<br/>车型/任务族/调度/交通/Coders]
|
|||
|
|
end
|
|||
|
|
subgraph L2[卫星 net8.0]
|
|||
|
|
Charge2[StandardScene.Charge]
|
|||
|
|
Devices2[StandardScene.Devices]
|
|||
|
|
VDA[StandardScene.Protocol.VDA5050]
|
|||
|
|
Nav[StandardScene.Nav.*(磁/二维码/激光,待内核放开)]
|
|||
|
|
end
|
|||
|
|
subgraph L3[宿主/接入 net8.0-windows]
|
|||
|
|
Web[StandardScene.WebApi(Nancy 隔离)]
|
|||
|
|
UI[StandardScene.UI.WinForms(临时·弃用,待 migu)]
|
|||
|
|
end
|
|||
|
|
Core2 --> Abstractions
|
|||
|
|
Core2 --> Infra
|
|||
|
|
Core2 --> Config
|
|||
|
|
Charge2 --> Abstractions
|
|||
|
|
Devices2 --> Abstractions
|
|||
|
|
VDA --> Abstractions
|
|||
|
|
Nav --> Abstractions
|
|||
|
|
Charge2 -. 受限 .-> Core2
|
|||
|
|
Web --> Core2
|
|||
|
|
UI --> Core2
|
|||
|
|
Devices2 -. NuGet .-> Modbus
|
|||
|
|
VDA -. NuGet .-> MQTT
|
|||
|
|
Web -. NuGet .-> Nancy
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
**关键规则**:
|
|||
|
|
1. **依赖只向下**:卫星/宿主 → Abstractions(+受限 Core);**Core 不得依赖任何具体协议/设备 NuGet**(MQTT/Modbus/IoTClient/OpenXml/Nancy 全部下放到对应卫星/宿主)。
|
|||
|
|
2. **抽象先行**:接口、注册特性、字段袋、纯领域模型、`ITrackCoder`/设备契约统一进 `Abstractions`(net8.0,无 Windows),卫星只认 Abstractions。
|
|||
|
|
3. **UI 与协议 = 边缘**:WinForms 全部收口到 `UI.WinForms`(标 deprecated,仅过渡,迁 migu 后删);Nancy 收口到 `WebApi`。如此 Abstractions/Infrastructure/Core/卫星可去 `-windows`,回到纯 `net8.0`。
|
|||
|
|
4. **发现统一**:设备/车型/协议统一"`[XxxType]` 特性 + `UiTypeDiscovery.AllTypes()`",`scene.json` 声明 `provides`。
|
|||
|
|
|
|||
|
|
### 4.2 边界接口(最小集)
|
|||
|
|
- `ILogger`(取代 `Console.WriteLine`/直连 Diagnosis):业务只依赖抽象。
|
|||
|
|
- `IDeviceDriver`/`IDoorController`/`IChargeStation`/`IButtonBox`(下沉 Abstractions),`IDisposable` 释放。
|
|||
|
|
- `MissionRunnerBase`(CancellationToken + 状态枚举 + 统一异常/日志):统一所有后台任务线程模型。
|
|||
|
|
- `ApiResult<T>`(统一 HTTP 响应),HTTP 鉴权中间件。
|
|||
|
|
- `IEndpointProvider`/配置注入:消灭硬编码 IP/URL/路径。
|
|||
|
|
- `ICarTransport`(车辆通信抽象):把 HttpClient 从车型类剥离,单例化。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 五、net8.0 去 Windows 依赖路径(解 S2)
|
|||
|
|
|
|||
|
|
1. **隔离 UI**:所有 `*Form/*Viewer/*Monitor + *.Designer.cs`(12+)迁 `StandardScene.UI.WinForms`(唯一 `net8.0-windows`+`UseWindowsForms`)。
|
|||
|
|
2. **去 MessageBox**:业务层 `MessageBox.Show`(Commons/Kiva/各 Manager)改为事件/`ILogger`,弹窗交 UI 层。
|
|||
|
|
3. **核对 Windows-only API**:去掉 CA1416 抑制后逐项消解(P/Invoke 控制台显隐等收口到宿主)。
|
|||
|
|
4. **切 TFM**:Abstractions/Infrastructure/Core/卫星改 `net8.0`;仅 UI 与(如需)宿主保留 `-windows`。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 六、分阶段迁移路径(低风险·每阶段 build-green·可回归)
|
|||
|
|
|
|||
|
|
> 延续既有"路线乙":**先结构移动(无逻辑变更)→ 再去重/解耦**,每步可独立验证。
|
|||
|
|
|
|||
|
|
- **A 抽象层奠基**:建 `StandardScene.Abstractions`,**纯移动**接口/特性/字段袋/纯模型(`ILoopRules`、`*TypeAttribute`、`BasicFields`、`LoopPoint/LoopTask` 等)。解 S6/S11。
|
|||
|
|
- **B 基础设施收口**:建 `Infrastructure`(TCP/Utils/CommonTools)+`ILogger`;修 `AsyncTcpClient` 异常类型/EndWrite。解 S1(部分)。
|
|||
|
|
- **C UI 隔离**:建 `UI.WinForms`,移走全部窗体;业务去 `MessageBox`。解 S2,打通去 `-windows`。
|
|||
|
|
- **D 协议/设备依赖下放**:MQTT→VDA5050、Modbus/IoTClient→Devices、Nancy→WebApi、OpenXml→报表所在卫星;Core.csproj 清空专有 NuGet。解 S1。
|
|||
|
|
- **E 充电独立**:抽 `StandardScene.Charge` 卫星(Mission/抽象/配置/通信),表单已在 UI 层。解 S4。
|
|||
|
|
- **F 任务线程统一**:落地 `MissionRunnerBase`,迁移 Scheduler/Chained/Charge 后台循环(在 P0-1 协作式停止基础上)。解 S3(并发面)。
|
|||
|
|
- **G WebApi 重构**:`ApiResult`+按资源拆分+鉴权中间件;老接口归 deprecated。解 S3/S9(WebApi)。
|
|||
|
|
- **H 巨类拆分**:AbstractLoopMission/ChainedDeliveryMission/AbstractChargeLogicMission/Kiva 按职责拆分。解 S3。
|
|||
|
|
- **I 切 net8.0 + 清死文件/绝对路径**:TFM 收敛;删 `AbstractChainedDeliveryMission` 等死文件;`HintPath` 改相对/包变量。解 S2/S9/S10。
|
|||
|
|
- **J 导航卫星(依赖内核)**:待内核放开 Coder 注册表(S8),抽磁/二维码/激光导航卫星。
|
|||
|
|
|
|||
|
|
每阶段出口标准:`dotnet build` 0 错误、警告不增、关键路径冒烟可过。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 七、模块处置矩阵(速查)
|
|||
|
|
|
|||
|
|
| 模块 | 现位置 | 目标位置 | 关键动作 |
|
|||
|
|
|---|---|---|---|
|
|||
|
|
| 接口/特性/字段袋/纯模型 | Core 各处 | **Abstractions** | 纯移动 |
|
|||
|
|
| TCP/Utils/CommonTools | Core | **Infrastructure** | 移动+`ILogger`+修 TCP |
|
|||
|
|
| 全部窗体/Viewer/Monitor | 各模块 | **UI.WinForms(deprecated)** | 移动+去 MessageBox |
|
|||
|
|
| 充电(任务/抽象/配置/通信) | Core/Charge | **StandardScene.Charge** | 卫星化 |
|
|||
|
|
| 充电桩具体驱动 | Devices | Devices 或并入 Charge | 统一 IDisposable |
|
|||
|
|
| 门/按钮盒 抽象+特性 | Core | Abstractions | 下沉 |
|
|||
|
|
| 门/按钮盒 驱动 | Devices | Devices | IDisposable |
|
|||
|
|
| MQTT/Modbus/IoTClient/Nancy/OpenXml | Core NuGet | 各卫星/WebApi | 依赖下放 |
|
|||
|
|
| WebApi | Core 单文件 | **StandardScene.WebApi** | 拆分+鉴权+ApiResult |
|
|||
|
|
| 车型 | Core/CarTypes | Core(领域) | 剥离通信/UI 协作者 |
|
|||
|
|
| Coders | Core/Coders | Core(→导航卫星 J 阶段) | 继续收敛 |
|
|||
|
|
| Commons/Heuristic/LadderLogic/CAD | Core 根 | 按职责归子模块 | 拆分+配置化 |
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 八、风险与约束
|
|||
|
|
|
|||
|
|
1. **内核耦合(SimpleLite/SimpleCore)**:Coder 注册表按内核程序集反射(S8)→导航卫星热插拔需内核改造;`UiTypeDiscovery.AllTypes()` 已支持跨程序集发现(设备/车型可行)。
|
|||
|
|
2. **无 Git 基线**:大量文件未纳入版本控制 → **强烈建议先建 Git 基线**再执行 A~J,保证可回滚。
|
|||
|
|
3. **行为等价**:车型/充电/VDA5050 含设备协议时序,移动需保持时序与字段语义(沿用"先移动后去重")。
|
|||
|
|
4. **绝对 HintPath/本地 dll**:迁移期保持 HintPath 可用,I 阶段统一相对化,避免中途断链。
|
|||
|
|
5. **migu 平台 UI**:UI.WinForms 仅过渡;接口层(Abstractions/WebApi)应面向 migu 提供稳定契约,UI 迁移后整包删除。
|
|||
|
|
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
## 九、近期可立即执行(已具备条件,低风险)
|
|||
|
|
1. 删除/归档死文件 `AbstractChainedDeliveryMission.cs`(已 Compile Remove)。
|
|||
|
|
2. 新建 `StandardScene.Abstractions`,先迁 `BasicFields`、`*TypeAttribute`、`Loop/ILoopRules`(解 S6/S11,且不改逻辑)。
|
|||
|
|
3. `MissionRunnerBase` 抽取(承接 P0-1 协作式停止成果,统一 Scheduler 四任务)。
|
|||
|
|
4. `ApiResult` 帮助器(先在 WebApi 内消重,零行为变化)。
|