From 14ac309b6e0c2f38911a182710d6525677cd56b6 Mon Sep 17 00:00:00 2001 From: GogoVega <92022724+GogoVega@users.noreply.github.com> Date: Tue, 2 Jul 2024 11:38:56 +0200 Subject: [PATCH 1/4] Fix menu to enable/disable selection when it's a group --- .../editor-client/src/js/ui/contextMenu.js | 18 +++++++++++------- 1 file changed, 11 insertions(+), 7 deletions(-) diff --git a/packages/node_modules/@node-red/editor-client/src/js/ui/contextMenu.js b/packages/node_modules/@node-red/editor-client/src/js/ui/contextMenu.js index dae3f6fa6..60615671e 100644 --- a/packages/node_modules/@node-red/editor-client/src/js/ui/contextMenu.js +++ b/packages/node_modules/@node-red/editor-client/src/js/ui/contextMenu.js @@ -32,24 +32,28 @@ RED.contextMenu = (function () { const canRemoveFromGroup = hasSelection && !!selection.nodes[0].g let hasGroup, isAllGroups = true, hasDisabledNode, hasEnabledNode, hasLabeledNode, hasUnlabeledNode; if (hasSelection) { - selection.nodes.forEach(n => { + const nodes = selection.nodes.slice(); + while (nodes.length) { + const n = nodes.shift(); if (n.type === 'group') { hasGroup = true; + nodes.push(...n.nodes); } else { isAllGroups = false; - } - if (n.d) { - hasDisabledNode = true; - } else { - hasEnabledNode = true; + if (n.d) { + hasDisabledNode = true; + } else { + hasEnabledNode = true; + } } if (n.l === undefined || n.l) { hasLabeledNode = true; } else { hasUnlabeledNode = true; } - }); + } } + const offset = $("#red-ui-workspace-chart").offset() let addX = options.x - offset.left + $("#red-ui-workspace-chart").scrollLeft() From 05c924a9df670843654f43787b1a5af36460b3f2 Mon Sep 17 00:00:00 2001 From: Dave Conway-Jones Date: Thu, 4 Jul 2024 15:09:55 +0100 Subject: [PATCH 2/4] Let batch node terminate "early" if msg.parts set to end of sequence (ie index = count -1). Useful to close at end of files etc. --- .../nodes/core/sequence/19-batch.html | 7 ++++- .../@node-red/nodes/core/sequence/19-batch.js | 8 +++++- .../nodes/locales/en-US/messages.json | 1 + test/nodes/core/sequence/19-batch_spec.js | 27 ++++++++++++++++--- 4 files changed, 37 insertions(+), 6 deletions(-) diff --git a/packages/node_modules/@node-red/nodes/core/sequence/19-batch.html b/packages/node_modules/@node-red/nodes/core/sequence/19-batch.html index 9afb84205..91e6567c5 100644 --- a/packages/node_modules/@node-red/nodes/core/sequence/19-batch.html +++ b/packages/node_modules/@node-red/nodes/core/sequence/19-batch.html @@ -36,6 +36,10 @@ +
+ + +
@@ -45,7 +49,7 @@
- +
@@ -101,6 +105,7 @@ } }, allowEmptySequence: {value:false}, + honourParts: {value:false}, topics: {value:[{topic:""}]} }, inputs:1, diff --git a/packages/node_modules/@node-red/nodes/core/sequence/19-batch.js b/packages/node_modules/@node-red/nodes/core/sequence/19-batch.js index f3f29df6a..5cc97e6a9 100644 --- a/packages/node_modules/@node-red/nodes/core/sequence/19-batch.js +++ b/packages/node_modules/@node-red/nodes/core/sequence/19-batch.js @@ -181,6 +181,8 @@ module.exports = function(RED) { RED.nodes.createNode(this,n); var node = this; var mode = n.mode || "count"; + var eof = false; + node.honourParts = n.honourParts || false; node.pending_count = 0; if (mode === "count") { @@ -201,9 +203,12 @@ module.exports = function(RED) { return; } var queue = node.pending; + if (node.honourParts && msg.hasOwnProperty("parts")) { + if (msg.parts.index + 1 === msg.parts.count) { eof = true; } + } queue.push({msg, send, done}); node.pending_count++; - if (queue.length === count) { + if (queue.length === count || eof === true) { send_msgs(node, queue, is_overlap); for (let i = 0; i < queue.length-overlap; i++) { queue[i].done(); @@ -211,6 +216,7 @@ module.exports = function(RED) { node.pending = (overlap === 0) ? [] : queue.slice(-overlap); node.pending_count = 0; + eof = false; } var max_msgs = max_kept_msgs_count(node); if ((max_msgs > 0) && (node.pending_count > max_msgs)) { diff --git a/packages/node_modules/@node-red/nodes/locales/en-US/messages.json b/packages/node_modules/@node-red/nodes/locales/en-US/messages.json index 560d192c1..37a249567 100644 --- a/packages/node_modules/@node-red/nodes/locales/en-US/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/en-US/messages.json @@ -1112,6 +1112,7 @@ "too-many": "too many pending messages in batch node", "unexpected": "unexpected mode", "no-parts": "no parts property in message", + "honourParts": "Allow msg.parts to also complete batch operation.", "error": { "invalid-count": "Invalid count", "invalid-overlap": "Invalid overlap", diff --git a/test/nodes/core/sequence/19-batch_spec.js b/test/nodes/core/sequence/19-batch_spec.js index 2ebcb8d4d..b4025a3f8 100644 --- a/test/nodes/core/sequence/19-batch_spec.js +++ b/test/nodes/core/sequence/19-batch_spec.js @@ -98,7 +98,7 @@ describe('BATCH node', function() { var n2 = helper.getNode("n2"); check_data(n1, n2, results, done); for(var i = 0; i < 6; i++) { - n1.receive({payload: i}); + n1.receive({payload: i, parts: { count:6, index:i }}); } }); } @@ -168,6 +168,25 @@ describe('BATCH node', function() { check_count(flow, results, done); }); + it('should create seq. with count (more sent than count)', function(done) { + var flow = [{id:"n1", type:"batch", name: "BatchNode", mode: "count", count: 4, overlap: 0, interval: 10, allowEmptySequence: false, topics: [], wires:[["n2"]]}, + {id:"n2", type:"helper"}]; + var results = [ + [0, 1, 2, 3] + ]; + check_count(flow, results, done); + }); + + it('should create seq. with count and terminate early if parts honoured', function(done) { + var flow = [{id:"n1", type:"batch", name: "BatchNode", mode: "count", count: 4, overlap: 0, interval: 10, allowEmptySequence:false, honourParts:true, topics: [], wires:[["n2"]]}, + {id:"n2", type:"helper"}]; + var results = [ + [0, 1, 2, 3], + [4, 5] + ]; + check_count(flow, results, done); + }); + it('should create seq. with count and overlap', function(done) { var flow = [{id:"n1", type:"batch", name: "BatchNode", mode: "count", count: 3, overlap: 2, interval: 10, allowEmptySequence: false, topics: [], wires:[["n2"]]}, {id:"n2", type:"helper"}]; @@ -455,7 +474,7 @@ describe('BATCH node', function() { function mapiDoneTestHelper(done, mode, count, overlap, interval, allowEmptySequence, msgAndTimings) { const completeNode = require("nr-test-utils").require("@node-red/nodes/core/common/24-complete.js"); const catchNode = require("nr-test-utils").require("@node-red/nodes/core/common/25-catch.js"); - const flow = [{id:"batchNode1", type:"batch", name: "BatchNode", mode, count, overlap, interval, + const flow = [{id:"batchNode1", type:"batch", name: "BatchNode", mode, count, overlap, interval, allowEmptySequence, topics: [{topic: "TA"}], wires:[[]]}, {id:"completeNode1",type:"complete",scope: ["batchNode1"],uncaught:false,wires:[["helperNode1"]]}, {id:"catchNode1", type:"catch",scope: ["batchNode1"],uncaught:false,wires:[["helperNode1"]]}, @@ -482,13 +501,13 @@ describe('BATCH node', function() { } it('should call done() when message is sent (mode: count)', function(done) { - mapiDoneTestHelper(done, "count", 2, 0, 2, false, [ + mapiDoneTestHelper(done, "count", 2, 0, 2, false, [ { msg: {payload: 0}, delay: 0, avr: 0, var: 100}, { msg: {payload: 1}, delay: 0, avr: 0, var: 100} ]); }); it('should call done() when reset (mode: count)', function(done) { - mapiDoneTestHelper(done, "count", 2, 0, 2, false, [ + mapiDoneTestHelper(done, "count", 2, 0, 2, false, [ { msg: {payload: 0}, delay: 0, avr: 200, var: 100}, { msg: {payload: 1, reset:true}, delay: 200, avr: 200, var: 100} ]); From ff35c46d5d6907abec79f8db8da3c800d561dc38 Mon Sep 17 00:00:00 2001 From: Dave Conway-Jones Date: Tue, 16 Jul 2024 14:37:16 +0100 Subject: [PATCH 3/4] Fix unintentianal Capitalisation in Split node to close #4832 --- .../nodes/core/sequence/17-split.html | 2 +- .../@node-red/nodes/locales/de/messages.json | 1 + .../nodes/locales/en-US/messages.json | 3 ++- .../@node-red/nodes/locales/ja/messages.json | 1 + .../nodes/locales/pt-BR/messages.json | 23 ++++++++++--------- .../@node-red/nodes/locales/ru/messages.json | 1 + .../nodes/locales/zh-CN/messages.json | 1 + .../nodes/locales/zh-TW/messages.json | 1 + 8 files changed, 20 insertions(+), 13 deletions(-) diff --git a/packages/node_modules/@node-red/nodes/core/sequence/17-split.html b/packages/node_modules/@node-red/nodes/core/sequence/17-split.html index d19be77f5..f1237231f 100644 --- a/packages/node_modules/@node-red/nodes/core/sequence/17-split.html +++ b/packages/node_modules/@node-red/nodes/core/sequence/17-split.html @@ -21,7 +21,7 @@
- +
diff --git a/packages/node_modules/@node-red/nodes/locales/de/messages.json b/packages/node_modules/@node-red/nodes/locales/de/messages.json index 051d65f47..a51e504cf 100644 --- a/packages/node_modules/@node-red/nodes/locales/de/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/de/messages.json @@ -912,6 +912,7 @@ "objectSend": "Sende eine Nachricht für jedes Schlüssel/Wert-Paar", "strBuff": "string / buffer", "array": "array", + "splitThe": "Split", "splitUsing": "Aufteilung", "splitLength": "feste Längen von", "stream": "Als Nachrichtenstrom behandeln (Streaming-Modus)", diff --git a/packages/node_modules/@node-red/nodes/locales/en-US/messages.json b/packages/node_modules/@node-red/nodes/locales/en-US/messages.json index 1c0ec6090..598e3536a 100644 --- a/packages/node_modules/@node-red/nodes/locales/en-US/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/en-US/messages.json @@ -1011,12 +1011,13 @@ "tip": "Tip: The filename should be an absolute path, otherwise it will be relative to the working directory of the Node-RED process." }, "split": { - "split": "Split", + "split": "split", "intro": "Split msg.payload based on type:", "object": "Object", "objectSend": "Send a message for each key/value pair", "strBuff": "String / Buffer", "array": "Array", + "splitThe": "Split the", "splitUsing": "Split using", "splitLength": "Fixed length of", "stream": "Handle as a stream of messages", diff --git a/packages/node_modules/@node-red/nodes/locales/ja/messages.json b/packages/node_modules/@node-red/nodes/locales/ja/messages.json index fe81a80ad..8d38ac077 100644 --- a/packages/node_modules/@node-red/nodes/locales/ja/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/ja/messages.json @@ -1017,6 +1017,7 @@ "objectSend": "各key/valueペアのメッセージを送信", "strBuff": "文字列 / バッファ", "array": "配列", + "splitThe": "に基づく", "splitUsing": "分割", "splitLength": "固定長", "stream": "メッセージのストリームとして処理", diff --git a/packages/node_modules/@node-red/nodes/locales/pt-BR/messages.json b/packages/node_modules/@node-red/nodes/locales/pt-BR/messages.json index 274053bc6..51e1fd897 100644 --- a/packages/node_modules/@node-red/nodes/locales/pt-BR/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/pt-BR/messages.json @@ -44,7 +44,7 @@ "global": "contexto global", "str": "Cadeia de caracteres", "num": "número", - "bool": "booliano", + "bool": "booliano", "json": "objeto", "bin": "Armazenamento temporário", "date": "Carimbo de data/hora", @@ -352,8 +352,8 @@ } }, "trigger": { - "send": "Enviar", - "then": "então", + "send": "Enviar", + "then": "então", "then-send": "então enviem", "output": { "string": "a cadeia de caracteres", @@ -446,7 +446,7 @@ "staticTopic": "Assinar um tópico único", "dynamicTopic": "Assinatura dinâmica", "auto-connect": "Conectar automaticamente", - "auto-mode-depreciated": "Esta opção está deprecada. Favor utilizar o novo modo de auto-detecção." + "auto-mode-depreciated": "Esta opção está deprecada. Favor utilizar o novo modo de auto-detecção." }, "sections-label": { "birth-message": "Mensagem enviada na conexão (mensagem de nascimento)", @@ -466,8 +466,8 @@ "close-topic": "Deixe em branco para desativar a mensagem de fechamento" }, "state": { - "connected": "Conectado ao negociante: _ broker _", - "disconnected": "Desconectado do negociante: _ broker _", + "connected": "Conectado ao negociante: _ broker _", + "disconnected": "Desconectado do negociante: _ broker _", "connect-failed": "Falha na conexão com o negociante: __broker__", "broker-disconnected": "Cliente de negociante __broker__ desconectado: __reasonCode__ __reasonString__" }, @@ -898,7 +898,7 @@ "o2j": "Objeto para opções JSON", "pretty": "Formatar cadeia de caracteres JSON", "action": "Ação", - "property": "Propriedade", + "property": "Propriedade", "actions": { "toggle": "Converter entre cadeia de caracteres JSON e Objeto", "str": "Sempre converter em cadeia de caracteres JSON", @@ -929,7 +929,7 @@ "write": "escrever arquivo", "read": "ler arquivo", "filename": "Nome do arquivo", - "path": "caminho", + "path": "caminho", "action": "Ação", "addnewline": "Adicionar nova linha (\\n) a cada carga útil?", "createdir": "Criar diretório se não existir?", @@ -994,6 +994,7 @@ "objectSend": "Envia uma mensagem para cada par chave/valor", "strBuff": "Cadeia de caracteres / Armazenamento Temporário", "array": "Matriz", + "splitThe": "Dividir", "splitUsing": "Dividir usando", "splitLength": "Comprimento fixo de", "stream": "Tratar como uma transmissão de mensagens", @@ -1066,9 +1067,9 @@ "batch" : { "batch": "lote", "mode": { - "label": "Modo", - "num-msgs": "Agrupar por número de mensagens", - "interval": "Agrupar por intervalo de tempo", + "label": "Modo", + "num-msgs": "Agrupar por número de mensagens", + "interval": "Agrupar por intervalo de tempo", "concat": "Concatenar sequências" }, "count": { diff --git a/packages/node_modules/@node-red/nodes/locales/ru/messages.json b/packages/node_modules/@node-red/nodes/locales/ru/messages.json index d2bb5777e..2694ac6a5 100644 --- a/packages/node_modules/@node-red/nodes/locales/ru/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/ru/messages.json @@ -874,6 +874,7 @@ "objectSend":"Отправлять сообщение для каждой пары ключ/значение", "strBuff":"Строка / Буфер", "array":"Массив", + "splitThe": "Pазделить", "splitUsing":"С помощью", "splitLength":"Фикс. длина", "stream":"Обрабатывать как поток сообщений", diff --git a/packages/node_modules/@node-red/nodes/locales/zh-CN/messages.json b/packages/node_modules/@node-red/nodes/locales/zh-CN/messages.json index 7a0ea4ae4..7d5616a8f 100644 --- a/packages/node_modules/@node-red/nodes/locales/zh-CN/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/zh-CN/messages.json @@ -997,6 +997,7 @@ "objectSend": "每个键值对作为单个消息发送", "strBuff": "字符串 / Buffer", "array": "数组", + "splitThe": "Split", "splitUsing": "拆分使用", "splitLength": "固定长度", "stream": "作为消息流处理", diff --git a/packages/node_modules/@node-red/nodes/locales/zh-TW/messages.json b/packages/node_modules/@node-red/nodes/locales/zh-TW/messages.json index f43531fb1..7d16c5817 100644 --- a/packages/node_modules/@node-red/nodes/locales/zh-TW/messages.json +++ b/packages/node_modules/@node-red/nodes/locales/zh-TW/messages.json @@ -866,6 +866,7 @@ "objectSend": "每個鍵值對作為單個消息發送", "strBuff": "字串 / Buffer", "array": "陣列", + "splitThe": "Split", "splitUsing": "拆分使用", "splitLength": "固定長度", "stream": "作為消息流處理", From 97ee6c67457ac3efd9184fc9a1e5e8d8685be384 Mon Sep 17 00:00:00 2001 From: Nick O'Leary Date: Thu, 18 Jul 2024 17:17:50 +0100 Subject: [PATCH 4/4] Back off node 22.5 --- .github/workflows/tests.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 70d36deb1..cf871716a 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -16,7 +16,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - node-version: [18, 20, 22] + node-version: [18, 20, 22.4.x] steps: - uses: actions/checkout@v4 - name: Use Node.js ${{ matrix.node-version }}