module.exports = function (RED) { function buildControlNamesFromRules(rules) { const names = []; if (!Array.isArray(rules)) { return names; } rules.forEach((rule) => { if (!rule) { return; } const type = (rule.t || rule.type || "eq").toString(); if (type === "idx") { const base = (rule.v || rule.base || "").trim(); if (!base) { return; } let from = parseInt(rule.from, 10); let to = parseInt(rule.to, 10); if (Number.isNaN(from) && Number.isNaN(to)) { return; } if (Number.isNaN(from)) { from = to; } if (Number.isNaN(to)) { to = from; } if (from > to) { const tmp = from; from = to; to = tmp; } for (let i = from; i <= to; i += 1) { names.push(base + i); } } else { const name = (rule.v || rule.value || "").trim(); if (name) { names.push(name); } } }); return names; } function normaliseAction(action) { const a = (action || "").toString().toLowerCase(); if (a === "unsubscribe" || a === "unsub") { return "UNSUBSCRIBE"; } return "SUBSCRIBE"; } function XilicaSubscribe(config) { RED.nodes.createNode(this, config); const node = this; node.action = config.action || "subscribe"; node.rules = Array.isArray(config.rules) ? config.rules : []; node.transport = config.transport || "TCP"; node.on("input", (msg, send, done) => { send = send || function () { node.send.apply(node, arguments); }; done = done || function () {}; const action = normaliseAction(msg.action || node.action); const rules = Array.isArray(msg.rules) ? msg.rules : node.rules; const transport = typeof msg.transport === "string" && msg.transport.trim().length ? msg.transport.trim() : node.transport; const names = buildControlNamesFromRules(rules); if (!names.length) { node.warn("xilica-subscribe: no rules defined"); send(msg); done(); return; } const lines = names.map( (name) => action + " " + name + ' "' + transport + '"', ); msg.payload = lines.join("\r"); send(msg); done(); }); } RED.nodes.registerType("xilica-subscribe", XilicaSubscribe); };