编辑 | blame | 历史 | 原始文档

MES 注塑机数采对接需求与设计

状态:待评审(评审通过后开始编码)
编写日期:2026-10-20
适用数据库:mom-kyzn
涉及模块:yudao-module-mes

1. 背景与目标

客户注塑机通过弘讯采集网关,将运行状态、周期过程、工艺参数、参数变更和报警以 MQTT 报文推送到 EMQX。当前 MES 没有任何 MQTT 接入代码,需要完成“订阅 → 解析 → 落库 → 查询/展示”的全链路对接,并把采集数据与 MES 设备台账、生产任务/工单关联起来。

本期目标(已与用户确认):

  1. 全量接入:realtime(实时状态)、spc(周期过程)、tech(工艺参数)、opLog(参数变更)、报警五类数据全部落库。
  2. 设备绑定:在 mes_dv_machinery 设备台账上增加“数采设备编号”,devId(如 C01)直接匹配台账。
  3. 工单联动:采集数据按“设备所属工作站上正在运行的生产任务”自动关联 taskId / workOrderId,关联不到时留空。
  4. 分级保留:原始报文 7 天、实时历史 30 天、周期/工艺/变更/报警长期保留。

不在本期范围:前端页面代码(按项目规则只输出联调方案)、设备反向控制(下行指令)、多实例共享订阅。

2. 接入信息

项目 值
EMQX 地址 36.213.90.123:1883(MQTT),18083(Dashboard/HTTP API)
账号 admin / public(Dashboard 与 MQTT 共用)
协议 MQTT 3.1.1,QoS 0
主题前缀 /YLCY/IMM(可配置)
设备编号 C01 ~ C08(devId)
订阅通配 {prefix}/+/+,即 /YLCY/IMM/+/+
客户端 ID 示例 /YLCY/IMM/C03/id

主题约定(来自采集文档):

数据类型 主题 说明
realtime {prefix}/{devId}/realtime 实时运行状态、温度、油温
spc {prefix}/{devId}/spc 每个注塑周期的过程数据
tech {prefix}/{devId}/tech 工艺设定参数全量快照
opLog {prefix}/{devId}/opLog 单个参数修改前后值
报警 文档未给出主题名 通过报文 topic 字段或 Data.wmId 识别;订阅通配兜底

说明:报警主题名在文档截图中缺失,因报文自带 topic 字段且 Data 中 wmId/wmMsg/wmTime 特征唯一,代码按报文特征识别,主题后缀仅作为配置项兜底,不阻塞接入。

3. 报文规范

3.1 公共信封

{
  "clientId": "/YLCY/IMM/C03/id",
  "devId": "C03",
  "topic": "realtime",
  "sendTime": "2026-09-24 11:37:00",
  "sendStamp": 1790221000000,
  "time": "2026-09-24 11:37:00",
  "timestamp": 1790221000000,
  "Data": { }
}
  • 数据时间优先取 time(yyyy-MM-dd HH:mm:ss),缺失时回退 timestamp。
  • Data 可能为对象;若为字符串,二次解析为对象。
  • 数据类型优先取 topic 字段,其次按主题后缀,最后按 Data 特征识别。

3.2 realtime(实时状态)

Data 示例字段:

编码 含义 备注
STS 状态 1 待机,2 生产
OPM 运行模式 0 手动,1 半自动,2 电眼自动,3 时间自动,4 调模使用
OT 油温
T1..Tn 各段温度 段数按实际为准,动态解析
ASTS 附加状态 原样保存

3.3 spc(周期过程数据)

编码 含义
CYCN 周期序号(部分系列独立计数,增量一致)
ECYCT 周期时间
EISS 射出起点
EIVM 最大射速
EIPM 最大射压
ESIPT 转保压时间
ESIPP 转保压压力
ESIPS 转保压位置
EIPT 射出时间
EIPSE 射出终点位置
EPLST 储料时间
EPLSSE 储料终点
EPLSPM 最大储料压力
ET1..ETn 生产温度(各段)

3.4 tech(工艺参数)

按文档第 3 节全量字段保存(TS/IP/IV/IS/IT/ITUSE/ISUSE/SIPT/SIPS/SIPP/PP/PV/PT/SBS/SBT/PLLT/PLV/PLP/PLBP/PLS/SBV/SBP/SBS/SBT/CT/MCV/MCP/MCS/MOV/MOP/MOS/EFDT/EFV/EFP/EFS/EBDT/EBV/EBP/EBS/CP1M~CP4M/CPI1S~CPI4S/CPI1P~CPI4P/CPI1V~CPI4V/CPI1T~CPI4T/CPO1S~CPO4S/CPO1P~CPO4P/CPO1V~CPO4V/CPO1T~CPO4T/CFP/CFV/CFS/CFT/CBP/CBV/CBS/CBT/CBDT)。字段数量多且可能扩展,**不建宽表**,整包 JSON 快照保存,前端按 JSON 渲染。

3.5 opLog(参数变更)

{
  "devId": "5",
  "time": "2022-12-09 12:09:48",
  "Data": {
    "varId": "SIPS",
    "value": 37.5,
    "lastValue": 37,
    "modifyTime": "2022-12-09 12:09:46"
  }
}

3.6 报警

{
  "devId": "6",
  "Data": {
    "wmId": 2,
    "wmMsg": "安全门未关",
    "wmTime": "2022-12-09 16:42:22"
  }
}
  • wmId = 2:报警产生 → 新增一条“未消除”记录。
  • wmId = 0:报警消失 → 把该设备所有“未消除”记录置为“已消除”,写入 clearTime。

4. 数据模型

所有新表沿用项目 BaseDO 字段:creator/create_time/updater/update_time/deleted。高频日志表按保留策略物理清理。

4.1 设备台账扩展

ALTER TABLE mes_dv_machinery
  ADD COLUMN collect_device_code VARCHAR(64) NULL COMMENT '数采设备编号(MQTT devId,如 C01)' AFTER workstation_id,
  ADD COLUMN collect_enabled BIT(1) NOT NULL DEFAULT b'0' COMMENT '是否启用数采' AFTER collect_device_code;

ALTER TABLE mes_dv_machinery
  ADD UNIQUE INDEX uk_collect_device_code (collect_device_code);
  • collect_device_code 为空表示未绑定数采。
  • 唯一索引允许多个 NULL,不会影响存量设备。
  • 关联任务时使用台账已有的 workstation_id。

4.2 新建表

表名 用途 保留
mes_collect_realtime 每设备最新实时状态(UPSERT) 常驻
mes_collect_realtime_history 实时状态历史 30 天
mes_collect_cycle 周期过程数据 长期
mes_collect_tech 工艺参数最新快照(UPSERT) 常驻
mes_collect_operate_log 参数变更日志 长期
mes_collect_alarm 报警记录 长期
mes_collect_message 原始报文(排障、补数依据) 7 天

关键字段:

  • mes_collect_realtime:device_code(唯一)、machinery_id、task_id、work_order_id、sts、opm、asts、ot、temps JSON、data_json、collect_time。
  • mes_collect_realtime_history:字段同上,唯一键 (device_code, collect_time),索引 (device_code, collect_time)、(work_order_id, collect_time)。
  • mes_collect_cycle:device_code、cycle_no、collect_time、ecyct/eiss/eivm/eipm/esipt/esipp/esips/eipt/eipse/eplst/eplsse/eplspm、et_temps JSON、data_json;唯一键 (device_code, cycle_no, collect_time)。
  • mes_collect_tech:device_code(唯一)、task_id、work_order_id、collect_time、data_json。
  • mes_collect_operate_log:device_code、var_id、old_value、new_value、modify_time、collect_time、data_json;索引 (device_code, modify_time)。
  • mes_collect_alarm:device_code、wm_id、wm_msg、wm_time、status(0 未消除/1 已消除)、clear_time、data_json;索引 (device_code, status)、(wm_time)。
  • mes_collect_message:device_code、machinery_id、mqtt_topic、msg_type、event_time、raw_payload LONGTEXT、process_status(0 成功/1 失败)、error_msg、receive_time。

4.3 落库规则

  • realtime:更新 mes_collect_realtime 快照 + 写 mes_collect_realtime_history(唯一键去重)。
  • spc:写 mes_collect_cycle(唯一键去重,INSERT IGNORE)。
  • tech:整包 JSON UPSERT mes_collect_tech;不重复生成变更日志,变更以设备上报的 opLog 为准。
  • opLog:逐条写 mes_collect_operate_log。
  • 报警:按 wmId 规则新增/清除。
  • 所有报文先写 mes_collect_message,解析失败也保留原文并记录 error_msg。
  • 未绑定台账的 devId:结构化数据照常入库(machinery_id/task_id/work_order_id 为空),原始报文保留,并以限流日志提示补绑台账,避免设备已上线但台账未维护时丢数据。

5. 工单自动关联

devId → mes_dv_machinery.collect_device_code → machinery.workstation_id
      → mes_pro_task(workstation_id 匹配、deleted=0、status IN (1 生产中, 2 部分完成, 9 已停工))
      → 取 last_feedback_time / id 最新的一条 → task_id + work_order_id
  • 结果缓存 30 秒(按 workstationId),避免每条报文查库。
  • 关联不到时 task_id / work_order_id 为空,不影响落库。
  • 任务切换后最多 30 秒延迟生效。

6. 后端实现设计

6.1 代码位置

yudao-module-mes/
├── controller/admin/collect/                  # 查询接口 + VO
├── service/collect/                           # 查询、解析、落库、关联
│   ├── MesCollectQueryService
│   ├── MesCollectDataService
│   ├── MesCollectMessageDispatcher
│   ├── MesCollectDataParser
│   ├── MesCollectTaskResolver
│   └── MesCollectCleanupJob(@Scheduled)
├── framework/collect/mqtt/MesCollectMqttClient # Paho 连接、订阅、重连
├── dal/dataobject/collect/                    # DO
└── dal/mysql/collect/                         # Mapper
  • MQTT 客户端使用项目依赖管理里已有的 org.eclipse.paho.client.mqttv3:1.2.5,在 yudao-module-mes/pom.xml 引入即可。
  • Paho 回调只做解析入队,落库放到单线程有界队列执行,避免阻塞心跳。
  • 开启 automaticReconnect,客户端 ID 使用 {prefix}-{hostname}-{random};**生产单实例部署**,多实例会重复消费(后续可改共享订阅)。
  • 通过 yudao.mes.collect.mqtt.enabled 控制是否连接,默认关闭,按环境开启。

6.2 配置项(application-kyzn.yaml,并同步 local/test)

yudao:
  mes:
    collect:
      mqtt:
        enabled: true
        url: tcp://36.213.90.123:1883
        username: admin
        password: public
        client-id-prefix: mes-collect
        topic-prefix: /YLCY/IMM
        qos: 0
        keep-alive: 65
        connection-timeout: 10
        alarm-topic-suffix: wm
      retention:
        raw-days: 7
        realtime-days: 30

6.3 清理任务

  • 每日 03:30 执行。
  • 物理删除 mes_collect_message 中 receive_time < now - 7 天、mes_collect_realtime_history 中 collect_time < now - 30 天 的数据。
  • 单次删除限制批量,避免长事务锁表。

7. 后端接口

统一前缀 /mes/collect,全部返回项目标准 CommonResult。

方法 路径 说明 权限
GET /device/list 设备数采状态列表(台账 + 最新状态 + 当前任务) mes:collect:query
GET /realtime/get 指定设备最新实时状态 mes:collect:query
GET /realtime/history-page 实时状态历史分页 mes:collect:query
GET /cycle/page 周期过程数据分页 mes:collect:query
GET /cycle/get 周期明细 mes:collect:query
GET /tech/get 指定设备最新工艺参数快照 mes:collect:query
GET /operate-log/page 参数变更分页 mes:collect:query
GET /alarm/page 报警分页 mes:collect:query
PUT /alarm/ack 手工确认报警 mes:collect-alarm:ack

设备绑定复用现有设备台账新增/更新接口,新增字段 collectDeviceCode、collectEnabled;台账分页支持按 collectDeviceCode 过滤。

8. 权限与菜单

  • 新增权限码:mes:collect:query、mes:collect-alarm:ack。
  • 菜单:设备管理(5300)下新增“数采监控”(collect/monitor)。
  • 同步写入 docs/sql/config_export_all_*.sql 与数据库初始化脚本,避免新库缺菜单/权限。
  • 按“权限码三方对齐”规则,菜单、角色授权、后端注解三处同时落地。

9. 部署与验证

  1. 执行 docs/sql/mes_collect_20261020.sql(本地 mom-kyzn 先执行验证;生产由运维执行)。
  2. 在设备台账填写 collect_device_code 并启用数采。
  3. 启动后端,确认日志出现 MQTT 连接成功、订阅成功。
  4. 观察 mes_collect_message 是否有各类型报文入库。
  5. 校验 mes_collect_realtime / cycle / tech / operate_log / alarm 数据与 EMQX 报文一致。
  6. 触发一次参数修改与报警,确认变更日志和报警状态流转正确。
  7. 验证工单关联:工作站存在生产中任务时,新数据的 task_id/work_order_id 不为空。

10. 风险与说明

  • 报警主题名缺失:按报文特征识别,已兜底;如后续确认主题名只需改配置。
  • CYCN 重置:周期序号可能随设备重启重置,去重键包含采集时间,避免误合并。
  • 多实例部署:当前为单实例消费,多实例会产生重复数据;后续可切换 EMQX 共享订阅。
  • 时钟偏差:设备时间与服务器时间可能不一致,事件时间以报文 time 为准,另存 receive_time。
  • 数据量:按 8 台设备、30 秒一帧估算,实时历史约 70 万行/月;如后续提高频率,需评估分区或改时序库。
  • 不修改前端代码:按项目规则另行输出前端联调方案。