291 lines
9.2 KiB
Markdown
291 lines
9.2 KiB
Markdown
# SecMPS 整合项目实施手册
|
||
|
||
> **版本**: v2.0
|
||
> **日期**: 2026-05-15
|
||
> **基于**: SecMPS_最终整合方案_v2.0.md
|
||
> **工期**: 18-20 个工作日
|
||
|
||
---
|
||
|
||
## 前置检查清单(Day 0)
|
||
|
||
| # | 检查项 | 验证方式 | 阻塞阶段 |
|
||
|---|--------|----------|----------|
|
||
| 1 | Owl+ZLM 部署运行 | 浏览器访问 Owl 管理端,确认可登录 | Phase 1 |
|
||
| 2 | 至少1台 GB28181 设备注册到 Owl | Owl 管理端 `/devices` 有数据 | Phase 1 |
|
||
| 3 | MC4.0 网关可访问 | `curl http://mc4_ip:3000/api/central/auth/conf/get` | Phase 2 |
|
||
| 4 | MC4.0 有设备接入 | 调对象树接口有 type=2 节点 | Phase 2 |
|
||
| 5 | Vol.Pro 代码生成器可用 | 新建测试表→运行生成器→确认生成 | Phase 0 |
|
||
| 6 | MySQL 有建表权限 | 直接执行 CREATE TABLE | Phase 0 |
|
||
| 7 | Node.js >= 20.19 | `node -v` | Phase 3 |
|
||
|
||
---
|
||
|
||
## Phase 0:基础设施搭建(Day 1-2)
|
||
|
||
### Day 1 — Gateway 骨架 + 数据库
|
||
|
||
**任务 1.1 — 创建 Gateway 解决方案**
|
||
|
||
```
|
||
dotnet new sln -n IntegrationGateway
|
||
dotnet new webapi -n IntegrationGateway.Host -f net8.0
|
||
dotnet new classlib -n IntegrationGateway.Core -f net8.0
|
||
```
|
||
|
||
**验证**: `dotnet build` 成功。
|
||
|
||
**任务 1.2 — Core 层接口**
|
||
|
||
创建 `Abstractions/`(7个接口文件)、`Models/`(8个模型文件)、`Infrastructure/`(AdapterRegistry/TokenManager/RateLimiter)。
|
||
|
||
**验证**: `dotnet build` 成功。编写单元测试:注册 mock 适配器,验证 Get() 返回非 null。
|
||
|
||
**任务 1.3 — Host 层 Controller**
|
||
|
||
创建 HealthController (`GET /api/gateway/health`)、DevicesController、PointsController、StreamsController、AlarmsController、SyncController。
|
||
|
||
**验证**: 启动 Host,`GET /api/gateway/health` 返回 200。
|
||
|
||
**任务 1.4 — 数据库建表(8张)**
|
||
|
||
按顺序执行 DDL:Base_Device → Device_Video_Ext → Video_Channel → Video_Record → Device_IoT_Ext → IoT_DevicePoint → IoT_DeviceData → IoT_Alarm。
|
||
|
||
**验证**:
|
||
```
|
||
SELECT COUNT(*) FROM Base_Device; → 0
|
||
SHOW INDEX FROM Base_Device WHERE Key_name LIKE '%Adapter%'; → 唯一索引存在
|
||
```
|
||
|
||
**任务 1.5 — 运行代码生成器**
|
||
|
||
对8张表运行 Vol.Pro 代码生成器。
|
||
|
||
**验证**: 管理端可看到8个新菜单,分别能正常 CRUD。
|
||
|
||
### Day 2 — Vol.Pro 侧 GatewayClient
|
||
|
||
**任务 2.1 — GatewayClient.cs**
|
||
|
||
实现 `IGatewayClient : IDependency`,封装对 Gateway 的 HTTP 调用。`appsettings.json` 添加 `"Gateway": {"BaseUrl": "http://localhost:5100"}`。
|
||
|
||
**验证**: 注入 IGatewayClient,调用 HealthCheckAsync() 返回 true。
|
||
|
||
**任务 2.2 — DeviceManagerController.cs**
|
||
|
||
创建 `Controllers/Warehouse/Partial/DeviceManagerController.cs`:
|
||
- `GET GetRegionTree` — 区域树+设备数量
|
||
- `GET GetDevicesByRegion?regionId=` — 设备列表含子设备
|
||
- `PUT {deviceId}` — 更新设备含地图绑定
|
||
|
||
**验证**: Postman 调 `GET /api/DeviceManager/GetRegionTree` 返回 JSON。
|
||
|
||
**任务 2.3 — SyncDevicesJob(Quartz)**
|
||
|
||
```csharp
|
||
public class SyncDevicesJob : IJob {
|
||
public async Task Execute(IJobExecutionContext ctx) {
|
||
var gw = ctx.GetService<IGatewayClient>();
|
||
var r = await gw.SyncDevicesAsync("mc4");
|
||
}
|
||
}
|
||
```
|
||
|
||
**验证**: Quartz 管理面板看到已注册 Job。
|
||
|
||
---
|
||
|
||
## Phase 1:Owl 适配器 + 视频设备页(Day 3-6)
|
||
|
||
### Day 3 — OwlAdapter
|
||
|
||
**任务 3.1**: 创建 `IntegrationGateway.Adapters.Owl` 项目。
|
||
|
||
**任务 3.2**: 实现 OwlAdapter(`IHasFlatDevices + IHasStreams + IAcceptsMetadataPush`)。
|
||
|
||
**验证(Postman 调 Gateway)**:
|
||
```
|
||
GET /api/gateway/health → {"owl": true}
|
||
GET /api/gateway/devices?adapter=owl&page=1 → 返回 Owl 设备列表
|
||
GET /api/gateway/streams/owl/{channelId}/live → 返回 WS-FLV 地址
|
||
```
|
||
|
||
**任务 3.3**: 端到端同步。调 `GET /api/gateway/devices/sync?adapter=owl`,查库 `SELECT * FROM Base_Device WHERE AdapterCode='owl'`,确认设备入库。
|
||
|
||
### Day 4 — 管理端设备页面框架
|
||
|
||
**任务 4.1**: 创建 `web.vite/src/views/warehouse/DeviceManager/` 目录。
|
||
|
||
**任务 4.2**: `index.vue` — 左右分栏布局(`el-container` → `el-aside` 280px + `el-main`)。
|
||
|
||
**任务 4.3**: `RegionTree.vue` — 调 `GetRegionTree`,渲染 `el-tree`,点击 emit `select(regionId)`。
|
||
|
||
**任务 4.4**: `DeviceTable.vue` — 调 `GetDevicesByRegion`,`el-table` 的 `tree-props` 展开子设备。
|
||
|
||
**验证**: 浏览器访问 `/device-manager`,左侧区域树+右侧设备表可用。
|
||
|
||
### Day 5 — 视频操作按钮 + 播放器
|
||
|
||
**任务 5.1**: `VideoDeviceActions.vue` — 实时预览/云台控制/查看回放 按钮。
|
||
|
||
**任务 5.2**: 安装 Jessibuca,创建 `DeviceLivePreview.vue` 弹窗+播放器。
|
||
|
||
**验证**: 点视频设备的「实时预览」→ 弹窗播放画面。
|
||
|
||
**任务 5.3**: 云台控制面板 — 方向键+停止,调 Gateway PTZ 接口。
|
||
|
||
**验证**: 点方向键 → 摄像机转动。
|
||
|
||
### Day 6 — 视频联调 + 边界测试
|
||
|
||
| 测试 | 预期 |
|
||
|------|------|
|
||
| 设备同步 | 表格数据刷新,不重复 |
|
||
| 实时预览 | Jessibuca 播放正常 |
|
||
| 云台控制 | 摄像机转动 |
|
||
| 多路播放(4路) | 不卡顿 |
|
||
| 离线设备 | 状态显示「离线」 |
|
||
| 框架隔离 | 重跑生成器,DeviceManager/ 文件未丢失 |
|
||
|
||
---
|
||
|
||
## Phase 2:MC4.0 适配器 + IoT 管理(Day 7-11)
|
||
|
||
### Day 7 — Mc4Adapter
|
||
|
||
创建 `IntegrationGateway.Adapters.MC4`,实现 `IHasOwnDeviceTree + IHasPoints + IHasAlarms`。
|
||
|
||
**验证(Postman 调 Gateway)**:
|
||
```
|
||
GET /api/gateway/health → {"mc4": true}
|
||
GET /api/gateway/devices/sync?adapter=mc4 → 同步报告
|
||
GET /api/gateway/realtime/mc4/{deviceId} → 点位值数组
|
||
POST /api/gateway/realtime/mc4/control {id,index,value} → 200
|
||
GET /api/gateway/alarms/mc4?from=...&to=... → 告警列表
|
||
POST /api/gateway/alarms/mc4/{id}/confirm → 确认成功
|
||
```
|
||
|
||
### Day 8 — 区域自动匹配 + 全量同步
|
||
|
||
实现 SyncEngine.ProcessTreeNode:type=1 节点 → MatchOrCreateRegion,type=2 节点 → UpsertDevice。
|
||
|
||
**验证**: 同步后 `warehouse_regions` 有 MC4.0 区域,`Base_Device.RegionId` 正确。
|
||
|
||
### Day 9 — IoT 操作按钮 + 实时数据
|
||
|
||
**任务 9.1**: `IoTDeviceActions.vue` — 实时数据/设备控制/告警记录 按钮。
|
||
|
||
**任务 9.2**: 实时数据弹窗 — 点位名称/当前值/单位/更新时间/控制控件。
|
||
|
||
**任务 9.3**: 设备控制 — 开关 `el-switch`,模拟量 `el-input-number`。
|
||
|
||
**验证**: 拖动滑块 → 设备实际值改变。
|
||
|
||
### Day 10 — 告警管理 + 地图绑定
|
||
|
||
**任务 10.1**: 编辑弹窗增加「告警记录」tab。
|
||
|
||
**任务 10.2**: `MapBindingPanel.vue` — MapModelId 选择、缩放/旋转、经纬度。
|
||
|
||
**验证**: 编辑设备 → 地图绑定 → 保存 → 值持久化。
|
||
|
||
### Day 11 — SignalR Hub + Quartz 轮询
|
||
|
||
**任务 11.1**: `IoTDataHub.cs` — SubscribeDevice/SubscribeAlarms。
|
||
|
||
**任务 11.2**: `RealtimePollJob.cs` (5s) + `AlarmPollJob.cs` (10s)。
|
||
|
||
**验证**: warehouse 端 SignalR 连接收到实时数据和告警推送。
|
||
|
||
---
|
||
|
||
## Phase 3:warehouse 端 + 全链路联调(Day 12-17)
|
||
|
||
### Day 12-13 — 视频播放器集成
|
||
|
||
- Live.vue: 假数据→真实 API + Jessibuca
|
||
- History.vue: 对接回放 API,HLS 播放
|
||
- VideoWall.vue: 9 路 WS-FLV
|
||
|
||
**验证**: Live/History/VideoWall 全功能可用。
|
||
|
||
### Day 14-15 — IoT 面板
|
||
|
||
- 实时数据看板:SignalR 订阅,每5秒更新
|
||
- 控制面板:开关/滑块,调控制 API
|
||
- 告警面板:实时弹窗+声音
|
||
|
||
**验证**: warehouse IoT 功能可用。
|
||
|
||
### Day 16-17 — 全链路联调
|
||
|
||
| 链路 | 预期 |
|
||
|------|------|
|
||
| 设备同步→入库 | Base_Device 有数据 |
|
||
| 区域树→el-tree | 层级正确 |
|
||
| 实时预览→播放 | 画面正常 |
|
||
| 云台→摄像机转动 | 方向正确 |
|
||
| 实时数据→面板 | 值更新 |
|
||
| 设备控制→设备响应 | 值改变 |
|
||
| 告警触发→弹窗 | <15秒 |
|
||
| 告警确认→MC4.0 | 状态变更 |
|
||
|
||
**性能指标**: 9路视频墙≥15fps,100设备轮询<3s,500设备同步<30s。
|
||
|
||
---
|
||
|
||
## Phase 4:验证 + 缓冲(Day 18-20)
|
||
|
||
### Day 18 — 代码隔离验证
|
||
|
||
1. 重跑代码生成器(对 Base_Device)
|
||
2. 检查 Partial/、extension/、DeviceManager/ 目录文件未覆盖
|
||
3. 检查生成文件已更新(新字段在编辑表单中出现)
|
||
|
||
### Day 19 — 异常场景
|
||
|
||
| 场景 | 预期 |
|
||
|------|------|
|
||
| Owl 宕机 | 不影响 MC4.0 同步 |
|
||
| MC4.0 宕机 | 页面不崩溃 |
|
||
| Gateway 宕机 | 前端错误提示 |
|
||
| Token 过期 | 自动刷新 |
|
||
| 并发同步 | 互不干扰 |
|
||
|
||
### Day 20 — 文档收尾
|
||
|
||
- [ ] API 文档(Swagger)
|
||
- [ ] 部署手册更新
|
||
- [ ] 组件使用说明
|
||
- [ ] 已知问题修复
|
||
|
||
---
|
||
|
||
## 附录:每日检查清单
|
||
|
||
```
|
||
□ 所有新增 C# 服务实现 IDependency
|
||
□ Controller 写在 Partial/ 目录
|
||
□ 前端扩展在 extension/ 目录
|
||
□ 未修改自动生成文件
|
||
□ MC4.0 调用经 RateLimiter
|
||
□ Owl Token 使用 TokenManager 缓存
|
||
□ 实时数据未写入 IoT_DeviceData
|
||
□ dotnet build 零错误
|
||
```
|
||
|
||
## 附录:端口分配
|
||
|
||
| 服务 | 端口 |
|
||
|------|------|
|
||
| IntegrationGateway | 5100 |
|
||
| VolPro.WebApi | 9100 |
|
||
| web.vite | 9000 |
|
||
| warehouse | 9200 |
|
||
| Owl | 80 |
|
||
| MC4.0 | 3000 |
|
||
|
||
---
|
||
|
||
> **文档结束**
|