smithtek-mako-rf 2.9.7 → 2.9.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "smithtek-mako-rf",
3
- "version": "2.9.7",
3
+ "version": "2.9.10",
4
4
  "description": "Smithtek dedicated node for communicating with the Mako PLC over RS485 or RF",
5
5
  "keywords": [
6
6
  "node-red",
Binary file
Binary file
@@ -117,7 +117,9 @@ module.exports = function (RED) {
117
117
  try { port.removeListener("data", onData); } catch (_e2) {}
118
118
  }
119
119
  try { if (typeof port.flush === "function") port.flush(() => {}); } catch (_e) {}
120
+ if (state._rssiCleanup === cleanup) delete state._rssiCleanup;
120
121
  }
122
+ state._rssiCleanup = cleanup;
121
123
 
122
124
  function onData(chunk) {
123
125
  rx = Buffer.concat([rx, Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk)]);
@@ -225,7 +227,16 @@ module.exports = function (RED) {
225
227
  const regIndex = Math.floor(byteOffset / 2);
226
228
 
227
229
  const w = (i) => (regs[i] & 0xffff);
230
+ const isBoolArray = (Array.isArray(regs) && typeof regs[0] === "boolean");
228
231
 
232
+ function coilWord(wordIndex) {
233
+ let out = 0;
234
+ const base = wordIndex * 16;
235
+ for (let b = 0; b < 16; b++) {
236
+ if (regs[base + b]) out |= (1 << b);
237
+ }
238
+ return out >>> 0;
239
+ }
229
240
  // 4 bytes from two 16-bit words in common Modbus orders
230
241
  function bytesABCD(a, b) {
231
242
  return Buffer.from([(a >> 8) & 0xff, a & 0xff, (b >> 8) & 0xff, b & 0xff]);
@@ -300,12 +311,25 @@ module.exports = function (RED) {
300
311
  return buf.readFloatBE(0);
301
312
  }
302
313
 
303
- case "digital to unsigned binary encoder":
304
- return w(regIndex) >>> 0;
314
+ case "digital to unsigned binary encoder": {
315
+ const word = w(regIndex) >>> 0;
316
+
317
+ // If the UI provided a bit (0–15), return that bit as TRUE/FALSE
318
+ const bit = clampInt(offsetBit, 0, 15, 0);
319
+ return ((word >> bit) & 1) === 1;
320
+ }
321
+
305
322
 
306
- // optional internal bool support
307
323
  case "bool": {
308
324
  const bit = clampInt(offsetBit, 0, 15, 0);
325
+
326
+ // If this is FC1/FC2 data (boolean array), read bit directly
327
+ if (isBoolArray) {
328
+ const idx = (regIndex * 16) + bit;
329
+ return !!regs[idx];
330
+ }
331
+
332
+ // Otherwise treat as 16-bit register
309
333
  return ((w(regIndex) >> bit) & 1) === 1;
310
334
  }
311
335
 
@@ -498,6 +522,7 @@ module.exports = function (RED) {
498
522
  state.busy = true;
499
523
 
500
524
  (async () => {
525
+ await sleep(20);
501
526
  while (state.queue.length > 0) {
502
527
  const item = state.queue.shift();
503
528
  const { node, msg, send, done, req, items } = item;
@@ -548,8 +573,9 @@ module.exports = function (RED) {
548
573
  // Force reconnect next attempt
549
574
  state.connected = false;
550
575
  try {
551
- state.client.close(() => {});
552
- } catch (_e) {}
576
+ await new Promise((resolve) => state.client.close(() => resolve()));
577
+ } catch (_e) {}
578
+
553
579
 
554
580
  if (attempt < totalTries && gap_s > 0) {
555
581
  await sleep(Math.floor(gap_s * 1000));
@@ -598,8 +624,12 @@ module.exports = function (RED) {
598
624
 
599
625
 
600
626
  const rssiDbm = await queryRssiOnSamePort(state, guardMs, timeoutMs);
627
+ await sleep(30);
601
628
  state.connected = false;
602
- try { state.client.close(() => {}); } catch (_e) {}
629
+ try {
630
+ await new Promise((resolve) => state.client.close(() => resolve()));
631
+ } catch (_e) {}
632
+
603
633
 
604
634
 
605
635
  const nodeKeyBase = sanitizeKey(node.name || busName || "mako_rf");
@@ -652,6 +682,7 @@ module.exports = function (RED) {
652
682
  this.gap_s = toNum(n.gap_s, 0);
653
683
  this.maxQueue = toNum(n.maxQueue, 50);
654
684
 
685
+ BUS.delete(this.id);
655
686
  ensureBusState(this);
656
687
 
657
688
  this.on("close", (removed, done) => {
@@ -769,9 +800,32 @@ module.exports = function (RED) {
769
800
  });
770
801
 
771
802
  node.on("close", function (_removed, done) {
803
+ try {
804
+ const busCfg = RED.nodes.getNode(config.bus);
805
+ if (busCfg) {
806
+ const s = BUS.get(busCfg.id);
807
+ if (s) {
808
+ // NEW: stop any in-flight queue processor from the old deploy
809
+ s.queue = [];
810
+ s.busy = false;
811
+
812
+ if (typeof s._rssiCleanup === "function") {
813
+ try { s._rssiCleanup(); } catch (_e) {}
814
+ }
815
+ if (s.client) {
816
+ try { s.client.close(() => {}); } catch (_e) {}
817
+ s.connected = false;
818
+ s.client = new (require("modbus-serial"))();
819
+ }
820
+ }
821
+ }
822
+ } catch (_e) {}
823
+
772
824
  node.status({});
773
825
  done();
774
826
  });
827
+
828
+
775
829
  }
776
830
 
777
831
  RED.nodes.registerType("smithtek-mako-rf", SmithtekMakoRfNode);
Binary file