node-red-contrib-mitsubishi 1.1.0

三菱 MC Protocol 3E/4E 采集节点 — 纯TCP零依赖, 支持Q/L/iQ-R/iQ-F/FX5U

npm install node-red-contrib-mitsubishi

node-red-contrib-mitsubishi

npm version license Node-RED

三菱 MC Protocol 3E/4E 以太网采集节点。一个节点读 N 个点位,零外部依赖,纯 TCP 实现。


截图

节点面板

配置面板

采集输出


为什么选这个节点?

痛点 其他 MC 节点 本节点
读 50 个点位 拖 50 个节点 拖 1 个节点,填表格
读 D200 是 FLOAT32 自己写 function 解码 表格选 FLOAT32,自动解码
原始值 2530 → 实际 253.0℃ 自己写 function 换算 填斜率 0.1,自动变换
PLC 返回错误码 0xC052 只会说 "timeout" "Address out of range"
serialNo 不递增 4E 帧可能串包 每帧自增 + 响应校验

特性

  • 独立可用 — 纯 Node.js net + Buffer,不依赖任何第三方库或后端服务
  • 表格编辑器 — 一个节点配置 N 个点位,自动按寄存器类型和地址聚类,合并为批量读取
  • 6 种数据类型 — INT16 / UINT16 / INT32 / UINT32 / FLOAT32 / BOOL
  • 8 种软元件 — D / W / R / X / Y / M / L / B,位元件(X/Y/M/L/B)自动逐位拆包
  • 斜率偏移变换engValue = rawValue × slope + offset,节点直接输出工程值
  • 4E serialNo 完整支持 — 每帧自增,响应校验,防止串包
  • 批量保护 — 单次读取字数超 960 自动拆包,防 PLC 报 0xC059
  • 错误诊断 — 19 个 MC 错误码映射为中文/英文可读信息
  • 模拟模式RED.settings.mcSimulationMode = true 不连 PLC 即可测试
  • 零依赖 — 仅使用 Node.js 内置 net + Buffer
  • 15+ 运行时 BUG 已修复 — 锁重入、异步异常、serialNo 首帧跳号、脏帧拦截、批量超限等

安装

cd ~/.node-red
npm install node-red-contrib-mitsubishi

重启 Node-RED,左侧节点栏出现 "三菱 PLC" 分类,包含两个节点:

节点 类型 说明
PLC 连接配置 config 存储 PLC IP、端口、帧格式等连接参数
MC 读取 input/output 配置点位表格,触发采集,输出数据

支持的 PLC

系列 帧格式 状态
Q 系列(QnU / QnUDV) 3E / 4E
L 系列 3E / 4E
iQ-R 4E
iQ-F(FX5U) 4E
FX3U + 以太网模块(FX3U-ENET) 3E
A 系列 1E / 2E ❌ (仅支持 3E/4E)

使用方法

1. 添加 PLC 连接配置

拖入 PLC 连接配置 节点,双击配置:

参数 默认值 说明
名称 PLC-1 显示名称
IP 地址 192.168.1.10 PLC 以太网模块 IP
端口 5007 3E 默认 5007 / 4E 默认 5008
帧格式 3E 3E(Q/L/FX3U)或 4E(iQ-R/iQ-F/FX5U)
网络号 0 多跳网络用,直连填 0
站号 0 目标站号,直连 CPU 填 0
超时 (ms) 3000 TCP 读写超时
重试次数 2 失败重试次数(不含首次)
重试间隔 (ms) 300 重试等待时间

2. 配置点位表格

拖入 MC 读取 节点,关联 PLC 配置,在表格中添加点位:

寄存器 地址 数据类型 斜率 偏移 名称
D 100 INT16 0.1 0 温度
D 200 FLOAT32 1 0 压力
X 0 BOOL 开关
D 300 UINT16 1 0 计数器

斜率/偏移公式engValue = rawValue × slope + offset

例如 PLC 存温度原始值 2530(实际 253.0℃),设斜率 = 0.1,偏移 = 0,输出 engValue = 253.0

3. 触发采集

inject 节点 → MC 读取节点,部署后点击 inject 按钮即可采集。

4. 动态点位(高级)

上游节点传入 msg.tags 会覆盖表格配置,适配 EdgeLink 采集管线:

msg.tags = [
  { id: "温度", regType: "D", addr: 100, dataType: "INT16", slope: 0.1, offset: 0 },
  { id: "压力", regType: "D", addr: 200, dataType: "FLOAT32" }
];

输出格式

正常采集

msg.payload = {
  success: true,
  deviceId: "PLC-1",          // 适配 edgelink-pg-store 动态分表
  data: {
    "温度": {
      rawValue: 2530,         // PLC 原始 int16
      engValue: 253.0,        // 解码后 × 斜率 + 偏移
      quality: 0,             // 0=正常 2=异常
      ts: "2026-06-30T08:00:00.000Z",
      regType: "D"            // 寄存器类型
    },
    "压力": {
      rawValue: 4123,
      engValue: 41.23,
      quality: 0,
      ts: "2026-06-30T08:00:00.000Z",
      regType: "D"
    },
    "开关": {
      rawValue: 1,
      engValue: 1,
      quality: 0,
      ts: "2026-06-30T08:00:00.000Z",
      regType: "X"
    }
  },
  error: null,
  driverType: "driver-mc-protocol",
  plcIp: "192.168.1.10",
  plcPort: 5007,
  roundTimeMs: 12
}

PLC 读取失败

msg.payload = {
  success: false,
  deviceId: "PLC-1",
  data: {},
  error: "[PLC 0xC052] Address out of range",
  driverType: "driver-mc-protocol",
  plcIp: "192.168.1.10",
  plcPort: 5007,
  roundTimeMs: 3012
}

网络故障

msg.payload = {
  success: false,
  deviceId: "PLC-1",
  data: {},
  error: "[NETWORK] TCP closed (no data)",
  ...
}

架构

┌──────────┐     ┌─────────────────────────────┐     ┌──────────┐
│ inject / │     │     mitsubishi-read          │     │ 三菱 PLC │
│ 动态tags │────→│                              │────→│          │
└──────────┘     │  1. 校验 + 清洗点位          │     │ Q / L /  │
                 │  2. 去重 + 聚类分组          │     │ iQ-R /   │
                 │  3. 逐组 3E/4E 帧请求        │     │ FX5U     │
                 │  4. 解码 + 斜率变换          │     └──────────┘
                 │  5. 输出 {raw,eng,quality}   │
                 └─────────────────────────────┘

 帧构造: build3EFrame / build4EFrame
 响应解析: parseMCResponse (subheader + endCode + serialNo + dataLen 校验)
 错误分类: 19 个 MC 错误码 + 网络错误 + 脏帧拦截
 锁机制: 按 host:port 维度全局锁,串行采集,60s 过期自释放

与 node-red-contrib-mcprotocol 对比

维度 本节点 mcprotocol
点位数量 N 个 / 节点 1 个 / 节点
批量优化 智能聚类合并 逐地址独立请求
数据类型 6 种 (INT16/UINT16/INT32/UINT32/FLOAT32/BOOL) 仅 INT16
位元件 自动拆包 不支持
斜率偏移变换 内置 rawValue × slope + offset
32位/浮点 自动读相邻寄存器 + 拼接
serialNo 每帧自增 + 回显校验 固定不变
错误诊断 19 个 MC 错误码可读 "timeout"
模拟模式 mcSimulationMode=true
deviceId 输出 ✅ 适配 pg-store 分表
regType 输出 ✅ 适配 pg-store 列映射
依赖 0 (纯 Node.js) mcprotocol 依赖
维护状态 ✅ 活跃 ⚠️ issue 长期未处理

模拟模式

在 Node-RED settings.js 中添加:

mcSimulationMode: true

重启后所有 MC 读取 节点不连 PLC,直接返回随机仿真数据。用于离线开发、CI 测试、Demo 演示。


与 EdgeLink 生态集成

┌──────────────────┐     ┌──────────────────────┐     ┌──────────────────┐
│ node-red-contrib │     │ node-red-contrib     │     │ PostgreSQL /     │
│ -mitsubishi      │────→│ -edgelink-pg         │────→│ TimescaleDB      │
│ (本节点)         │     │ (PG 批量写入)        │     │                  │
└──────────────────┘     └──────────────────────┘     └──────────────────┘

本节点输出的 deviceIdregTyperawValueengValuequalityts 字段可由 edgelink-pg-store 自动识别为 MC 驱动格式,零配置写入数据库。


FAQ

Q: 为什么不用连接池?
MC 协议是无状态短连接。每次采集建立 TCP → 发送帧 → 接收响应 → 关闭。用连接池不会带来性能提升(TCP 握手开销远小于 PLC 扫描周期),反而有状态泄漏风险。

Q: 能同时读多个 PLC 吗?
可以。每个 PLC 连接配置 配置一个 PLC。多个 MC 读取 节点关联不同配置即可。全局锁按 host:port 隔离,不同 PLC 并行执行。

Q: 点位地址能写成 "D100" 格式吗?
可以。地址字段兼容 "D100" 格式(自动提取数字部分),也支持纯数字 100

Q: switch 元素一次最多读多少个点位?
字元件单次最多 960 字,位元件单次最多 15360 点。超出自动拆组,无需手动干预。

Q: 支持 FX3U 吗?
带以太网模块(FX3U-ENET)支持 3E 帧。不带以太网模块的 FX3U 不支持(需要 1E 帧或串口)。


许可证

MIT · 可自由商用、修改、再发布

Node Info

Version: 1.1.0
Updated 1 day ago
License: MIT
Rating: 5.0 2

Categories

Actions

Rate:

Downloads

317 in the last week

Nodes

  • mitsubishi-config
  • mitsubishi-read

Keywords

  • node-red
  • mitsubishi
  • mc-protocol
  • plc
  • 3e
  • 4e
  • melsec
  • industrial
  • iot
  • edgelink

Maintainers