跳转到内容

多输出 Function 节点

多输出 Function 节点

本节介绍如何使用 Function 节点的多输出功能。学习完成后,您将能够:

  • 配置 Function 节点的多输出端口
  • 实现条件分流的数据处理
  • 设计多分支数据流
  • 理解多输出与 Switch 节点的协作

Function 节点可以配置多个输出端口,每个端口发送不同的数据:

[Function Node (3 outputs)]
┌───┼───┐
│ │ │
▼ ▼ ▼
[DB] [MQTT] [Alert]
// 在节点属性中:
// Outputs: 2 (设置输出端口数量)
// 代码返回数组:
// [output1_msg, output2_msg, ...]
// null = 该输出不发送消息
// 3 个输出端口
// 输出 1: 正常温度数据
// 输出 2: 高温告警
// 输出 3: 低温告警
var temp = msg.payload.temperature;
if (temp > 30) {
// 高温告警 → 输出 2
return [
null, // 输出 1: 不发送
{ payload: { alert: "HIGH_TEMP", value: temp } },
null // 输出 3: 不发送
];
} else if (temp < 10) {
// 低温告警 → 输出 3
return [
null,
null,
{ payload: { alert: "LOW_TEMP", value: temp } }
];
} else {
// 正常数据 → 输出 1
return [
{ payload: { temperature: temp, status: "normal" } },
null,
null
];
}
// 2 个输出端口
// 输出 1: 存储到 InfluxDB
// 输出 2: 实时推送 Dashboard
var data = msg.payload;
// 输出 1: InfluxDB 格式
var dbMsg = {
payload: {
measurement: "sensor_data",
tags: { device: data.device },
fields: { temperature: data.temp, humidity: data.hum }
}
};
// 输出 2: Dashboard 格式
var dashMsg = {
payload: {
device: data.device,
temperature: data.temp,
humidity: data.hum,
timestamp: new Date().toLocaleTimeString()
}
};
return [dbMsg, dashMsg];
// 2 个输出端口
// 输出 1: 业务处理
// 输出 2: 审计日志
var deviceId = msg.topic;
var value = msg.payload;
// 业务消息 (输出 1)
var businessMsg = {
payload: {
device: deviceId,
command: value > 50 ? "cooling_on" : "normal",
value: value
}
};
// 日志消息 (输出 2)
var logMsg = {
payload: {
timestamp: Date.now(),
device: deviceId,
value: value,
action: "data_received"
}
};
return [businessMsg, logMsg];

将 Switch 条件判断与 Function 多输出结合:

[Switch Node] ──→ [Function (多输出)]
│ │
│ 条件 1 输出 1
│ 条件 2 输出 2
│ 条件 3 输出 3
// Function 节点根据消息来源处理
switch (msg.topic) {
case "sensor/temperature":
// 输出 1: 温度处理
return [{ payload: { type: "temp", value: msg.payload } }, null, null];
case "sensor/humidity":
// 输出 2: 湿度处理
return [null, { payload: { type: "hum", value: msg.payload } }, null];
case "sensor/pressure":
// 输出 3: 气压处理
return [null, null, { payload: { type: "pres", value: msg.payload } }];
default:
node.warn("Unknown topic: " + msg.topic);
return [null, null, null]; // 所有输出都不发送
}

完整的多输出 Flow:

→ [InfluxDB Out: 数据存储]
[MQTT In] → [Function (3 outputs)] → [MQTT Out: 设备控制]
→ [Email: 告警通知]
// Function 节点代码
var temp = parseFloat(msg.payload.temperature || msg.payload);
// 存储消息 (输出 1)
var storeMsg = {
payload: {
measurement: "temperature",
fields: { value: temp },
timestamp: Date.now()
}
};
// 控制消息 (输出 2)
var controlMsg = null;
if (temp > 35) {
controlMsg = {
payload: { command: "cooling_on", value: temp }
};
}
// 告警消息 (输出 3)
var alertMsg = null;
if (temp > 40) {
alertMsg = {
payload: {
severity: "critical",
message: "Temperature critical: " + temp + "°C",
timestamp: new Date().toISOString()
}
};
}
return [storeMsg, controlMsg, alertMsg];
// 在每个输出前添加 Debug 节点
// 便于跟踪各分支的数据流
// 在 Function 中添加日志
node.warn("Output 1 (Store): " + JSON.stringify(storeMsg));
node.warn("Output 2 (Control): " + JSON.stringify(controlMsg));
node.warn("Output 3 (Alert): " + JSON.stringify(alertMsg));

推荐做法:

  • 多输出与多分支配对应保持清晰
  • 用 null 明确表示不发送的分支
  • 在 Function 中添加注释说明各输出用途
  • 使用 Debug 节点验证每个输出
  • 各输出数据格式保持一致性

避免做法:

  • 同时使用超过 5 个输出端口
  • 输出端口用途不明确
  • 忘记在数组中使用正确的顺序
  • 各输出数据处理不一致
  • 不处理异常情况
  1. Function 节点支持多个输出端口
  2. 返回数组格式 [output1, output2, …]
  3. null 表示该输出不发送消息
  4. 多输出适合数据分发、条件分流场景
  5. 结合 Switch 节点可以实现复杂的路由逻辑