@5minds/node-red-contrib-processcube 1.7.7-feature-fae782-m6wffu2k → 1.8.0-feature-6eed29-m6wgknb1

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.
@@ -429,10 +429,21 @@
429
429
  },
430
430
  "@5minds/node-red-contrib-processcube": {
431
431
  "name": "@5minds/node-red-contrib-processcube",
432
- "version": "2.0.0",
432
+ "version": "1.8.0",
433
433
  "local": false,
434
434
  "user": false,
435
435
  "nodes": {
436
+ "checkAuthorization": {
437
+ "name": "checkAuthorization",
438
+ "types": [
439
+ "check-authorization"
440
+ ],
441
+ "enabled": true,
442
+ "local": false,
443
+ "user": false,
444
+ "module": "@5minds/node-red-contrib-processcube",
445
+ "file": "/usr/src/node-red/node_modules/@5minds/node-red-contrib-processcube/check-authorization.js"
446
+ },
436
447
  "EndEventFinishedListener": {
437
448
  "name": "EndEventFinishedListener",
438
449
  "types": [
@@ -444,6 +455,17 @@
444
455
  "module": "@5minds/node-red-contrib-processcube",
445
456
  "file": "/usr/src/node-red/node_modules/@5minds/node-red-contrib-processcube/endevent-finished-listener.js"
446
457
  },
458
+ "ExternalTaskInputInject": {
459
+ "name": "ExternalTaskInputInject",
460
+ "types": [
461
+ "externaltask-input-inject"
462
+ ],
463
+ "enabled": true,
464
+ "local": false,
465
+ "user": false,
466
+ "module": "@5minds/node-red-contrib-processcube",
467
+ "file": "/usr/src/node-red/node_modules/@5minds/node-red-contrib-processcube/externaltask-input-inject.js"
468
+ },
447
469
  "externaltaskInput": {
448
470
  "name": "externaltaskInput",
449
471
  "types": [
@@ -111,6 +111,14 @@
111
111
  "info": "",
112
112
  "env": []
113
113
  },
114
+ {
115
+ "id": "17865ef049c3b83d",
116
+ "type": "tab",
117
+ "label": "External Task Testing",
118
+ "disabled": false,
119
+ "info": "",
120
+ "env": []
121
+ },
114
122
  {
115
123
  "id": "8eb64bb58f95989d",
116
124
  "type": "subflow",
@@ -3231,5 +3239,132 @@
3231
3239
  "af52431420fa7e15"
3232
3240
  ]
3233
3241
  ]
3242
+ },
3243
+ {
3244
+ "id": "d75f8915b26e8f52",
3245
+ "type": "externaltask-input-inject",
3246
+ "z": "17865ef049c3b83d",
3247
+ "name": "a",
3248
+ "externaltask": "476cbb99633a9539",
3249
+ "x": 370,
3250
+ "y": 320,
3251
+ "wires": [
3252
+ [
3253
+ "1afda17294a69742"
3254
+ ]
3255
+ ]
3256
+ },
3257
+ {
3258
+ "id": "3c50b6d63b7b81d8",
3259
+ "type": "inject",
3260
+ "z": "17865ef049c3b83d",
3261
+ "name": "",
3262
+ "props": [
3263
+ {
3264
+ "p": "payload"
3265
+ }
3266
+ ],
3267
+ "repeat": "",
3268
+ "crontab": "",
3269
+ "once": false,
3270
+ "onceDelay": 0.1,
3271
+ "topic": "",
3272
+ "payload": "{\"hello\":\"world\"}",
3273
+ "payloadType": "json",
3274
+ "x": 160,
3275
+ "y": 320,
3276
+ "wires": [
3277
+ [
3278
+ "d75f8915b26e8f52"
3279
+ ]
3280
+ ]
3281
+ },
3282
+ {
3283
+ "id": "1afda17294a69742",
3284
+ "type": "debug",
3285
+ "z": "17865ef049c3b83d",
3286
+ "name": "debug 4",
3287
+ "active": true,
3288
+ "tosidebar": true,
3289
+ "console": false,
3290
+ "tostatus": false,
3291
+ "complete": "false",
3292
+ "statusVal": "",
3293
+ "statusType": "auto",
3294
+ "x": 560,
3295
+ "y": 320,
3296
+ "wires": []
3297
+ },
3298
+ {
3299
+ "id": "476cbb99633a9539",
3300
+ "type": "externaltask-input",
3301
+ "z": "17865ef049c3b83d",
3302
+ "name": "test inject",
3303
+ "engine": "b78932d162d8d468",
3304
+ "topic": "test",
3305
+ "topicType": "str",
3306
+ "workerConfig": "{}",
3307
+ "workerConfigType": "json",
3308
+ "x": 220,
3309
+ "y": 140,
3310
+ "wires": [
3311
+ [
3312
+ "36c31ae7ce4b2536"
3313
+ ]
3314
+ ]
3315
+ },
3316
+ {
3317
+ "id": "dd8e11733ed305c1",
3318
+ "type": "externaltask-output",
3319
+ "z": "17865ef049c3b83d",
3320
+ "name": "",
3321
+ "x": 670,
3322
+ "y": 200,
3323
+ "wires": []
3324
+ },
3325
+ {
3326
+ "id": "36c31ae7ce4b2536",
3327
+ "type": "delay",
3328
+ "z": "17865ef049c3b83d",
3329
+ "name": "",
3330
+ "pauseType": "delay",
3331
+ "timeout": "5",
3332
+ "timeoutUnits": "seconds",
3333
+ "rate": "1",
3334
+ "nbRateUnits": "1",
3335
+ "rateUnits": "second",
3336
+ "randomFirst": "1",
3337
+ "randomLast": "5",
3338
+ "randomUnits": "seconds",
3339
+ "drop": false,
3340
+ "allowrate": false,
3341
+ "outputs": 1,
3342
+ "x": 400,
3343
+ "y": 140,
3344
+ "wires": [
3345
+ [
3346
+ "59f385728d7d350d"
3347
+ ]
3348
+ ]
3349
+ },
3350
+ {
3351
+ "id": "59f385728d7d350d",
3352
+ "type": "function",
3353
+ "z": "17865ef049c3b83d",
3354
+ "name": "function 1",
3355
+ "func": "msg.payload.running = \"1\";\nmsg.payload.at = new Date().toISOString();\nreturn msg;",
3356
+ "outputs": 1,
3357
+ "timeout": 0,
3358
+ "noerr": 0,
3359
+ "initialize": "",
3360
+ "finalize": "",
3361
+ "libs": [],
3362
+ "x": 580,
3363
+ "y": 120,
3364
+ "wires": [
3365
+ [
3366
+ "dd8e11733ed305c1"
3367
+ ]
3368
+ ]
3234
3369
  }
3235
3370
  ]
@@ -393,7 +393,7 @@ module.exports = {
393
393
  * If not set, the following default order is used:
394
394
  */
395
395
  //categories: ['subflows', 'common', 'function', 'network', 'sequence', 'parser', 'storage'],
396
- categories: ['ProcessCube', 'ProcessCube Events', 'ProcessCube UI', 'dashboard 2'],
396
+ categories: ['ProcessCube', 'ProcessCube Events', 'ProcessCube UI', 'ProcessCube Testing', 'ProcessCube DevOps', 'dashboard 2'],
397
397
  },
398
398
 
399
399
  projects: {
@@ -0,0 +1,143 @@
1
+ [
2
+ {
3
+ "id": "17865ef049c3b83d",
4
+ "type": "tab",
5
+ "label": "External Task Testing",
6
+ "disabled": false,
7
+ "info": "",
8
+ "env": []
9
+ },
10
+ {
11
+ "id": "d75f8915b26e8f52",
12
+ "type": "externaltask-input-inject",
13
+ "z": "17865ef049c3b83d",
14
+ "name": "a",
15
+ "externaltask": "476cbb99633a9539",
16
+ "x": 370,
17
+ "y": 320,
18
+ "wires": [
19
+ [
20
+ "1afda17294a69742"
21
+ ]
22
+ ]
23
+ },
24
+ {
25
+ "id": "3c50b6d63b7b81d8",
26
+ "type": "inject",
27
+ "z": "17865ef049c3b83d",
28
+ "name": "",
29
+ "props": [
30
+ {
31
+ "p": "payload"
32
+ }
33
+ ],
34
+ "repeat": "",
35
+ "crontab": "",
36
+ "once": false,
37
+ "onceDelay": 0.1,
38
+ "topic": "",
39
+ "payload": "{\"hello\":\"world\"}",
40
+ "payloadType": "json",
41
+ "x": 160,
42
+ "y": 320,
43
+ "wires": [
44
+ [
45
+ "d75f8915b26e8f52"
46
+ ]
47
+ ]
48
+ },
49
+ {
50
+ "id": "1afda17294a69742",
51
+ "type": "debug",
52
+ "z": "17865ef049c3b83d",
53
+ "name": "debug 4",
54
+ "active": true,
55
+ "tosidebar": true,
56
+ "console": false,
57
+ "tostatus": false,
58
+ "complete": "false",
59
+ "statusVal": "",
60
+ "statusType": "auto",
61
+ "x": 560,
62
+ "y": 320,
63
+ "wires": []
64
+ },
65
+ {
66
+ "id": "476cbb99633a9539",
67
+ "type": "externaltask-input",
68
+ "z": "17865ef049c3b83d",
69
+ "name": "test inject",
70
+ "engine": "b78932d162d8d468",
71
+ "topic": "test",
72
+ "topicType": "str",
73
+ "workerConfig": "{}",
74
+ "workerConfigType": "json",
75
+ "x": 220,
76
+ "y": 140,
77
+ "wires": [
78
+ [
79
+ "36c31ae7ce4b2536"
80
+ ]
81
+ ]
82
+ },
83
+ {
84
+ "id": "dd8e11733ed305c1",
85
+ "type": "externaltask-output",
86
+ "z": "17865ef049c3b83d",
87
+ "name": "",
88
+ "x": 670,
89
+ "y": 200,
90
+ "wires": []
91
+ },
92
+ {
93
+ "id": "36c31ae7ce4b2536",
94
+ "type": "delay",
95
+ "z": "17865ef049c3b83d",
96
+ "name": "",
97
+ "pauseType": "delay",
98
+ "timeout": "5",
99
+ "timeoutUnits": "seconds",
100
+ "rate": "1",
101
+ "nbRateUnits": "1",
102
+ "rateUnits": "second",
103
+ "randomFirst": "1",
104
+ "randomLast": "5",
105
+ "randomUnits": "seconds",
106
+ "drop": false,
107
+ "allowrate": false,
108
+ "outputs": 1,
109
+ "x": 400,
110
+ "y": 140,
111
+ "wires": [
112
+ [
113
+ "59f385728d7d350d"
114
+ ]
115
+ ]
116
+ },
117
+ {
118
+ "id": "59f385728d7d350d",
119
+ "type": "function",
120
+ "z": "17865ef049c3b83d",
121
+ "name": "function 1",
122
+ "func": "msg.payload.running = \"1\";\nmsg.payload.at = new Date().toISOString();\nreturn msg;",
123
+ "outputs": 1,
124
+ "timeout": 0,
125
+ "noerr": 0,
126
+ "initialize": "",
127
+ "finalize": "",
128
+ "libs": [],
129
+ "x": 580,
130
+ "y": 120,
131
+ "wires": [
132
+ [
133
+ "dd8e11733ed305c1"
134
+ ]
135
+ ]
136
+ },
137
+ {
138
+ "id": "b78932d162d8d468",
139
+ "type": "processcube-engine-config",
140
+ "name": "Engine Auth 8000",
141
+ "url": "http://engine:8000"
142
+ }
143
+ ]
@@ -0,0 +1,100 @@
1
+ <script type="text/javascript">
2
+ RED.nodes.registerType('externaltask-input-inject', {
3
+ category: 'ProcessCube Testing',
4
+ color: '#02AFD6',
5
+ defaults: {
6
+ name: { value: '' },
7
+ externaltask: { value: '' }
8
+ },
9
+ inputs: 1,
10
+ outputs: 1,
11
+ icon: 'externaltask_input.svg',
12
+ label: function () {
13
+ const nodes = RED.nodes.filterNodes({ type: 'externaltask-input' });
14
+
15
+ if (nodes && nodes.length > 0) {
16
+ let foundNode = null;
17
+ nodes.forEach((node) => {
18
+ if (node.id === this.externaltask) {
19
+ foundNode = node;
20
+ }
21
+ });
22
+
23
+ return foundNode ? `inject '${foundNode.name}'` : this.name || 'externaltask-input-inject';
24
+ } else {
25
+ return this.name || 'externaltask-input-inject';
26
+ }
27
+ },
28
+ oneditprepare: function () {
29
+
30
+ try {
31
+ var dropdown = $('#node-input-externaltask');
32
+ dropdown.empty();
33
+ const selectedValue = this.externaltask || "";
34
+
35
+
36
+ const localCallNodes = RED.nodes.filterNodes({ type: 'externaltask-input' });
37
+ if (!Array.isArray(localCallNodes)) {
38
+ console.error("Expected an array from RED.nodes.filterNodes but got:", localCallNodes);
39
+ return;
40
+ }
41
+
42
+ if (localCallNodes.length === 0) {
43
+ console.warn("No externaltask-input nodes found.");
44
+ dropdown.append($("<option></option>").attr("value", "").text("No available tasks"));
45
+ } else {
46
+ localCallNodes.forEach((node) => {
47
+ let option = $("<option></option>")
48
+ .attr("value", node.id)
49
+ .text(`${node.name || "Unnamed"} (${node.id})`);
50
+
51
+ if (node.id === selectedValue) {
52
+ option.attr("selected", "selected");
53
+ }
54
+
55
+ dropdown.append(option);
56
+ });
57
+ }
58
+
59
+ } catch (error) {
60
+ console.error(error);
61
+ }
62
+ },
63
+ oneditsave: function () {
64
+ this.externaltask = $('#node-input-externaltask').val();
65
+ }
66
+ });
67
+ </script>
68
+
69
+ <script type="text/html" data-template-name="externaltask-input-inject">
70
+ <div class="form-row">
71
+ <label for="node-input-name"><i class="fa fa-tag"></i> Name</label>
72
+ <input type="text" id="node-input-name" placeholder="Name" />
73
+ </div>
74
+ <div class="form-row">
75
+ <label for="node-input-externaltask"><i class="fa fa-tag"></i> External Task</label>
76
+ <select id="node-input-externaltask"></select>
77
+ </div>
78
+ </script>
79
+
80
+ <script type="text/markdown" data-help-name="externaltask-input-inject">
81
+ Send the incoming message to the external task.
82
+
83
+ ## Configs
84
+
85
+ : name (string) : The name of the node
86
+ : externaltask (external-input) : The External task to inject the message
87
+
88
+ ## Input
89
+
90
+ : payload (string | {}) : The payload to send to the external task.
91
+
92
+ ## Outputs
93
+
94
+ : payload (string | {}) : The payload the result from the external task.
95
+
96
+ ### References
97
+
98
+ - [The ProcessCube&copy; Developer Network](https://processcube.io) - All documentation for the ProcessCube&copy; platform
99
+ - [ProcessCube&copy; LowCode Integration](https://processcube.io/docs/node-red) - LowCode integration in ProcessCube&copy;
100
+ </script>
@@ -0,0 +1,38 @@
1
+ module.exports = function (RED) {
2
+ function ExternalTaskInputInject(config) {
3
+ RED.nodes.createNode(this, config);
4
+ var node = this;
5
+
6
+ node.config = config;
7
+
8
+
9
+ node.on('input', async function (msg, send, done) {
10
+ node.externalTask = RED.nodes.getNode(node.config.externaltask);
11
+
12
+ if (node.externalTask) {
13
+ node.log(`Received message: ${JSON.stringify(msg)} and send to external task ${node.externalTask.id}.`);
14
+
15
+ node.externalTask.injectNodeCallback = (msg) => {
16
+ send(msg);
17
+ done()
18
+ }
19
+
20
+ if (node.externalTask.injectCall) {
21
+ node.externalTask.injectCall(msg).catch((error) => {
22
+ node.error(`Error in inject call: ${error.message}`, {});
23
+ done(`Error in inject call: ${error.message}`);
24
+ });
25
+ } else {
26
+ node.error('No inject call found.');
27
+ done('No inject call found.');
28
+ }
29
+ } else {
30
+ node.error('No external task node found.');
31
+ done('No external task node found.');
32
+ }
33
+ });
34
+
35
+ }
36
+
37
+ RED.nodes.registerType('externaltask-input-inject', ExternalTaskInputInject);
38
+ };
@@ -22,6 +22,32 @@ module.exports = function (RED) {
22
22
 
23
23
  node.eventEmitter = new EventEmitter();
24
24
 
25
+ // for external-task-inject
26
+ node.injectNodeCallback = null;
27
+ node.injectCall = null; // will be build in the register function
28
+
29
+ const buildMessage = (msg, externalTask, payload) => {
30
+ let newMsg = msg;
31
+
32
+ if (!newMsg) {
33
+ newMsg = {
34
+ _msgid: RED.util.generateId(),
35
+ };
36
+ }
37
+
38
+ newMsg.task = RED.util.encodeObject(externalTask);
39
+ newMsg.payload = payload;
40
+ newMsg.flowNodeInstanceId = externalTask.flowNodeInstanceId;
41
+ newMsg.processInstanceId = externalTask.processInstanceId;
42
+ newMsg.etw_input_node_id = node.id;
43
+
44
+ if (externalTask._injectCall) {
45
+ newMsg._injectCall = true;
46
+ }
47
+
48
+ return newMsg;
49
+ }
50
+
25
51
  const register = async () => {
26
52
  if (node.etw) {
27
53
  try {
@@ -64,7 +90,6 @@ module.exports = function (RED) {
64
90
 
65
91
  showStatus(node, Object.keys(node.started_external_tasks).length);
66
92
 
67
- //resolve(result);
68
93
  saveHandleCallback(result, resolve);
69
94
  };
70
95
 
@@ -81,8 +106,6 @@ module.exports = function (RED) {
81
106
 
82
107
  // TODO: with reject, the default error handling is proceed
83
108
  // SEE: https://github.com/5minds/ProcessCube.Engine.Client.ts/blob/develop/src/ExternalTaskWorker.ts#L180
84
- // reject(result);
85
- //resolve(msg);
86
109
  saveHandleCallback(msg, resolve);
87
110
  };
88
111
 
@@ -91,17 +114,34 @@ module.exports = function (RED) {
91
114
  `handle event for *external task flowNodeInstanceId* '${externalTask.flowNodeInstanceId}' and *processInstanceId* '${externalTask.processInstanceId}' with *msg._msgid* '${msg._msgid}' and *isError* '${isError}'`
92
115
  );
93
116
 
94
- if (isError) {
95
- handleErrorTask(msg);
117
+ if (msg._injectCall) {
118
+ if (node.injectNodeCallback) {
119
+ node.injectNodeCallback(msg);
120
+ } else {
121
+ node.error('No injectCall function defined.', {});
122
+ }
123
+
124
+ if (externalTask.flowNodeInstanceId) {
125
+ delete node.started_external_tasks[externalTask.flowNodeInstanceId];
126
+ showStatus(node, Object.keys(node.started_external_tasks).length);
127
+ }
128
+
96
129
  } else {
97
- handleFinishTask(msg);
130
+ if (isError) {
131
+ handleErrorTask(msg);
132
+ } else {
133
+ handleFinishTask(msg);
134
+ }
135
+
98
136
  }
137
+
99
138
  });
100
139
 
101
140
  node.started_external_tasks[externalTask.flowNodeInstanceId] = externalTask;
102
141
 
103
142
  showStatus(node, Object.keys(node.started_external_tasks).length);
104
143
 
144
+ /*
105
145
  let msg = {
106
146
  _msgid: RED.util.generateId(),
107
147
  task: RED.util.encodeObject(externalTask),
@@ -110,6 +150,9 @@ module.exports = function (RED) {
110
150
  processInstanceId: externalTask.processInstanceId,
111
151
  etw_input_node_id: node.id,
112
152
  };
153
+ */
154
+
155
+ let msg = buildMessage(null, externalTask, payload);
113
156
 
114
157
  node.log(
115
158
  `Received *external task flowNodeInstanceId* '${externalTask.flowNodeInstanceId}' and *processInstanceId* '${externalTask.processInstanceId}' with *msg._msgid* '${msg._msgid}'`
@@ -122,6 +165,17 @@ module.exports = function (RED) {
122
165
  let options = RED.util.evaluateNodeProperty(config.workerConfig, config.workerConfigType, node);
123
166
  let topic = RED.util.evaluateNodeProperty(config.topic, config.topicType, node)
124
167
 
168
+ node.injectCall = async (msg) => {
169
+ const genericTask = {
170
+ task: {},
171
+ flowNodeInstanceId: msg._msgid,
172
+ processInstanceId: msg._msgid,
173
+ _injectCall: true
174
+ };
175
+
176
+ await etwCallback(msg, genericTask);
177
+ };
178
+
125
179
  client.externalTasks
126
180
  .subscribeToExternalTaskTopic(topic, etwCallback, options)
127
181
  .then(async (externalTaskWorker) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@5minds/node-red-contrib-processcube",
3
- "version": "1.7.7-feature-fae782-m6wffu2k",
3
+ "version": "1.8.0-feature-6eed29-m6wgknb1",
4
4
  "license": "MIT",
5
5
  "description": "Node-RED nodes for ProcessCube",
6
6
  "scripts": {
@@ -37,6 +37,7 @@
37
37
  "nodes": {
38
38
  "checkAuthorization": "check-authorization.js",
39
39
  "EndEventFinishedListener": "endevent-finished-listener.js",
40
+ "ExternalTaskInputInject": "externaltask-input-inject.js",
40
41
  "externaltaskInput": "externaltask-input.js",
41
42
  "externaltaskOutput": "externaltask-output.js",
42
43
  "externaltaskError": "externaltask-error.js",