@5minds/node-red-contrib-processcube-tools 1.2.0-develop-2eb127-mg68t7xt → 1.2.0-develop-59ef22-mg9d9ja5
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/.mocharc.json +5 -0
- package/package.json +26 -10
- package/src/custom-node-template/custom-node-template.html.template +45 -0
- package/src/custom-node-template/custom-node-template.ts.template +69 -0
- package/src/email-receiver/email-receiver.ts +439 -0
- package/src/email-sender/email-sender.ts +210 -0
- package/{processcube-html-to-text/processcube-html-to-text.html → src/html-to-text/html-to-text.html} +3 -3
- package/src/html-to-text/html-to-text.ts +53 -0
- package/src/index.ts +12 -0
- package/src/interfaces/EmailReceiverMessage.ts +22 -0
- package/src/interfaces/EmailSenderNodeProperties.ts +37 -0
- package/src/interfaces/FetchState.ts +9 -0
- package/src/interfaces/ImapConnectionConfig.ts +14 -0
- package/src/test/framework/advanced-test-patterns.ts +224 -0
- package/src/test/framework/generic-node-test-suite.ts +58 -0
- package/src/test/framework/index.ts +17 -0
- package/src/test/framework/integration-assertions.ts +67 -0
- package/src/test/framework/integration-scenario-builder.ts +77 -0
- package/src/test/framework/integration-test-runner.ts +101 -0
- package/src/test/framework/node-assertions.ts +63 -0
- package/src/test/framework/node-test-runner.ts +260 -0
- package/src/test/framework/test-scenario-builder.ts +74 -0
- package/src/test/framework/types.ts +61 -0
- package/src/test/helpers/email-receiver-test-configs.ts +67 -0
- package/src/test/helpers/email-receiver-test-flows.ts +16 -0
- package/src/test/helpers/email-sender-test-configs.ts +123 -0
- package/src/test/helpers/email-sender-test-flows.ts +16 -0
- package/src/test/integration/email-receiver.integration.test.ts +41 -0
- package/src/test/integration/email-sender.integration.test.ts +129 -0
- package/src/test/interfaces/email-data.ts +10 -0
- package/src/test/interfaces/email-receiver-config.ts +12 -0
- package/src/test/interfaces/email-sender-config.ts +26 -0
- package/src/test/interfaces/imap-config.ts +9 -0
- package/src/test/interfaces/imap-mailbox.ts +5 -0
- package/src/test/interfaces/mail-options.ts +20 -0
- package/src/test/interfaces/parsed-email.ts +11 -0
- package/src/test/interfaces/send-mail-result.ts +7 -0
- package/src/test/mocks/imap-mock.ts +147 -0
- package/src/test/mocks/mailparser-mock.ts +82 -0
- package/src/test/mocks/nodemailer-mock.ts +118 -0
- package/src/test/unit/email-receiver.unit.test.ts +471 -0
- package/src/test/unit/email-sender.unit.test.ts +550 -0
- package/tsconfig.json +23 -0
- package/email-receiver/email-receiver.js +0 -304
- package/email-sender/email-sender.js +0 -178
- package/examples/.gitkeep +0 -0
- package/processcube-html-to-text/processcube-html-to-text.js +0 -22
- package/test/helpers/email-receiver.mocks.js +0 -447
- package/test/helpers/email-sender.mocks.js +0 -368
- package/test/integration/email-receiver.integration.test.js +0 -515
- package/test/integration/email-sender.integration.test.js +0 -239
- package/test/unit/email-receiver.unit.test.js +0 -304
- package/test/unit/email-sender.unit.test.js +0 -570
- /package/{email-receiver → src/email-receiver}/email-receiver.html +0 -0
- /package/{email-sender → src/email-sender}/email-sender.html +0 -0
|
@@ -1,515 +0,0 @@
|
|
|
1
|
-
const { expect } = require('chai');
|
|
2
|
-
const helper = require('node-red-node-test-helper');
|
|
3
|
-
const {
|
|
4
|
-
createMockImap,
|
|
5
|
-
createMockMailparser,
|
|
6
|
-
setupModuleMocks,
|
|
7
|
-
testConfigs,
|
|
8
|
-
testFlows,
|
|
9
|
-
testUtils,
|
|
10
|
-
} = require('../helpers/email-receiver.mocks.js');
|
|
11
|
-
|
|
12
|
-
describe('E-Mail Receiver Node - Integration Tests', function () {
|
|
13
|
-
// Set a reasonable timeout for integration tests
|
|
14
|
-
this.timeout(10000);
|
|
15
|
-
|
|
16
|
-
let emailReceiverNode;
|
|
17
|
-
let cleanupMocks;
|
|
18
|
-
|
|
19
|
-
before(function (done) {
|
|
20
|
-
// Set up mocks using helper
|
|
21
|
-
cleanupMocks = setupModuleMocks();
|
|
22
|
-
|
|
23
|
-
// Load the node with mocked dependencies
|
|
24
|
-
emailReceiverNode = require('../../email-receiver/email-receiver.js');
|
|
25
|
-
|
|
26
|
-
// CRITICAL: Initialize the helper with Node-RED
|
|
27
|
-
helper.init(require.resolve('node-red'));
|
|
28
|
-
done();
|
|
29
|
-
});
|
|
30
|
-
|
|
31
|
-
after(function () {
|
|
32
|
-
// Clean up mocks using helper cleanup function
|
|
33
|
-
if (cleanupMocks) {
|
|
34
|
-
cleanupMocks();
|
|
35
|
-
}
|
|
36
|
-
});
|
|
37
|
-
|
|
38
|
-
beforeEach(function (done) {
|
|
39
|
-
helper.startServer(done);
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
afterEach(function (done) {
|
|
43
|
-
helper.unload();
|
|
44
|
-
helper.stopServer(done);
|
|
45
|
-
});
|
|
46
|
-
|
|
47
|
-
describe('Node Loading', function () {
|
|
48
|
-
it('should load in Node-RED test environment', function (done) {
|
|
49
|
-
// ARRANGE: Use test flow from helpers
|
|
50
|
-
const flow = [testConfigs.valid];
|
|
51
|
-
|
|
52
|
-
// ACT: Load the node in the test helper environment
|
|
53
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
54
|
-
try {
|
|
55
|
-
// ASSERT: Verify the node loaded correctly
|
|
56
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
57
|
-
expect(n1).to.exist;
|
|
58
|
-
expect(n1).to.have.property('name', testConfigs.valid.name);
|
|
59
|
-
expect(n1).to.have.property('type', 'email-receiver');
|
|
60
|
-
done();
|
|
61
|
-
} catch (err) {
|
|
62
|
-
done(err);
|
|
63
|
-
}
|
|
64
|
-
});
|
|
65
|
-
});
|
|
66
|
-
|
|
67
|
-
it('should load with minimal configuration', function (done) {
|
|
68
|
-
// ARRANGE: Use minimal test config from helpers
|
|
69
|
-
const flow = [testConfigs.minimal];
|
|
70
|
-
|
|
71
|
-
// ACT: Load the node
|
|
72
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
73
|
-
try {
|
|
74
|
-
// ASSERT: Verify the node loaded with minimal config
|
|
75
|
-
const n1 = helper.getNode(testConfigs.minimal.id);
|
|
76
|
-
expect(n1).to.exist;
|
|
77
|
-
expect(n1).to.have.property('type', 'email-receiver');
|
|
78
|
-
done();
|
|
79
|
-
} catch (err) {
|
|
80
|
-
done(err);
|
|
81
|
-
}
|
|
82
|
-
});
|
|
83
|
-
});
|
|
84
|
-
|
|
85
|
-
it('should load with array folders configuration', function (done) {
|
|
86
|
-
// ARRANGE: Use array folders config from helpers
|
|
87
|
-
const flow = [testConfigs.arrayFolders];
|
|
88
|
-
|
|
89
|
-
// ACT: Load the node
|
|
90
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
91
|
-
try {
|
|
92
|
-
// ASSERT: Verify the node loaded with array folders
|
|
93
|
-
const n1 = helper.getNode(testConfigs.arrayFolders.id);
|
|
94
|
-
expect(n1).to.exist;
|
|
95
|
-
expect(n1).to.have.property('name', testConfigs.arrayFolders.name);
|
|
96
|
-
done();
|
|
97
|
-
} catch (err) {
|
|
98
|
-
done(err);
|
|
99
|
-
}
|
|
100
|
-
});
|
|
101
|
-
});
|
|
102
|
-
});
|
|
103
|
-
|
|
104
|
-
describe('Node Connections', function () {
|
|
105
|
-
it('should create wired connections correctly', function (done) {
|
|
106
|
-
// ARRANGE: Use connected test flow from helpers
|
|
107
|
-
const flow = testFlows.connected;
|
|
108
|
-
|
|
109
|
-
// ACT: Load nodes and verify connections
|
|
110
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
111
|
-
try {
|
|
112
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
113
|
-
const h1 = helper.getNode('h1');
|
|
114
|
-
|
|
115
|
-
// ASSERT: Both nodes should exist and be connected
|
|
116
|
-
expect(n1).to.exist;
|
|
117
|
-
expect(h1).to.exist;
|
|
118
|
-
expect(n1).to.have.property('name', testConfigs.valid.name);
|
|
119
|
-
expect(h1).to.have.property('type', 'helper');
|
|
120
|
-
|
|
121
|
-
done();
|
|
122
|
-
} catch (err) {
|
|
123
|
-
done(err);
|
|
124
|
-
}
|
|
125
|
-
});
|
|
126
|
-
});
|
|
127
|
-
|
|
128
|
-
it('should handle multiple output connections', function (done) {
|
|
129
|
-
// ARRANGE: Use multi-output test flow from helpers
|
|
130
|
-
const flow = testFlows.multiOutput;
|
|
131
|
-
|
|
132
|
-
// ACT: Load nodes
|
|
133
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
134
|
-
try {
|
|
135
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
136
|
-
const h1 = helper.getNode('h1');
|
|
137
|
-
const h2 = helper.getNode('h2');
|
|
138
|
-
|
|
139
|
-
// ASSERT: All nodes should exist
|
|
140
|
-
expect(n1).to.exist;
|
|
141
|
-
expect(h1).to.exist;
|
|
142
|
-
expect(h2).to.exist;
|
|
143
|
-
expect(n1).to.have.property('name', testConfigs.valid.name);
|
|
144
|
-
|
|
145
|
-
done();
|
|
146
|
-
} catch (err) {
|
|
147
|
-
done(err);
|
|
148
|
-
}
|
|
149
|
-
});
|
|
150
|
-
});
|
|
151
|
-
});
|
|
152
|
-
|
|
153
|
-
describe('Message Flow', function () {
|
|
154
|
-
it('should handle input without crashing', async function () {
|
|
155
|
-
// ARRANGE: Use test flow from helpers
|
|
156
|
-
const flow = testFlows.single;
|
|
157
|
-
|
|
158
|
-
return new Promise((resolve, reject) => {
|
|
159
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
160
|
-
try {
|
|
161
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
162
|
-
expect(n1).to.exist;
|
|
163
|
-
|
|
164
|
-
// Send input - this should not crash due to mocked IMAP
|
|
165
|
-
n1.receive({ payload: 'test input' });
|
|
166
|
-
|
|
167
|
-
// ASSERT: If we reach here, the node handled input gracefully
|
|
168
|
-
testUtils.wait(500).then(() => {
|
|
169
|
-
resolve(); // Success if no errors thrown
|
|
170
|
-
});
|
|
171
|
-
} catch (err) {
|
|
172
|
-
reject(err);
|
|
173
|
-
}
|
|
174
|
-
});
|
|
175
|
-
});
|
|
176
|
-
});
|
|
177
|
-
|
|
178
|
-
it('should process messages through connected nodes', function (done) {
|
|
179
|
-
// ARRANGE: Use connected test flow from helpers
|
|
180
|
-
const flow = testFlows.connected;
|
|
181
|
-
|
|
182
|
-
// ACT: Load nodes and set up message listener
|
|
183
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
184
|
-
try {
|
|
185
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
186
|
-
const h1 = helper.getNode('h1');
|
|
187
|
-
|
|
188
|
-
// Set up listener for messages from email receiver
|
|
189
|
-
h1.on('input', function (msg) {
|
|
190
|
-
try {
|
|
191
|
-
// ASSERT: Should receive a message with expected properties
|
|
192
|
-
expect(msg).to.exist;
|
|
193
|
-
expect(msg.payload).to.exist;
|
|
194
|
-
done();
|
|
195
|
-
} catch (err) {
|
|
196
|
-
done(err);
|
|
197
|
-
}
|
|
198
|
-
});
|
|
199
|
-
|
|
200
|
-
// Simulate the email processing
|
|
201
|
-
// The email-receiver node likely starts processing emails automatically
|
|
202
|
-
// Let's trigger the mock IMAP flow by simulating what happens when emails are found
|
|
203
|
-
setTimeout(() => {
|
|
204
|
-
// Simulate the email receiver processing emails and sending a message
|
|
205
|
-
// This is what your email-receiver node should do internally
|
|
206
|
-
try {
|
|
207
|
-
const mockEmailMessage = {
|
|
208
|
-
payload: 'This is a mock email body for testing purposes.',
|
|
209
|
-
topic: 'email',
|
|
210
|
-
from: 'sender@test.com',
|
|
211
|
-
subject: 'Mock Email Subject',
|
|
212
|
-
};
|
|
213
|
-
|
|
214
|
-
// Directly send a message through the node (simulating internal processing)
|
|
215
|
-
n1.send(mockEmailMessage);
|
|
216
|
-
} catch (err) {
|
|
217
|
-
done(err);
|
|
218
|
-
}
|
|
219
|
-
}, 100);
|
|
220
|
-
} catch (err) {
|
|
221
|
-
done(err);
|
|
222
|
-
}
|
|
223
|
-
});
|
|
224
|
-
});
|
|
225
|
-
|
|
226
|
-
it('should handle message timeout gracefully', async function () {
|
|
227
|
-
// ARRANGE: Use connected test flow
|
|
228
|
-
const flow = testFlows.connected;
|
|
229
|
-
|
|
230
|
-
return new Promise((resolve, reject) => {
|
|
231
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
232
|
-
try {
|
|
233
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
234
|
-
const h1 = helper.getNode('h1');
|
|
235
|
-
|
|
236
|
-
// Use testUtils.waitForMessage with timeout
|
|
237
|
-
testUtils
|
|
238
|
-
.waitForMessage(h1, 1000)
|
|
239
|
-
.then((msg) => {
|
|
240
|
-
// ASSERT: Should receive message within timeout
|
|
241
|
-
expect(msg).to.exist;
|
|
242
|
-
resolve();
|
|
243
|
-
})
|
|
244
|
-
.catch((err) => {
|
|
245
|
-
// ASSERT: Should handle timeout appropriately
|
|
246
|
-
expect(err.message).to.include('Timeout waiting for message');
|
|
247
|
-
resolve(); // This is expected behavior for this test
|
|
248
|
-
});
|
|
249
|
-
|
|
250
|
-
// Don't trigger anything to test timeout behavior
|
|
251
|
-
// The timeout should occur as expected
|
|
252
|
-
} catch (err) {
|
|
253
|
-
reject(err);
|
|
254
|
-
}
|
|
255
|
-
});
|
|
256
|
-
});
|
|
257
|
-
});
|
|
258
|
-
|
|
259
|
-
it('should process emails and send messages when emails are received', function (done) {
|
|
260
|
-
const flow = testFlows.connected;
|
|
261
|
-
|
|
262
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
263
|
-
try {
|
|
264
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
265
|
-
const h1 = helper.getNode('h1');
|
|
266
|
-
|
|
267
|
-
h1.on('input', function (msg) {
|
|
268
|
-
try {
|
|
269
|
-
expect(msg).to.exist;
|
|
270
|
-
expect(msg.payload).to.exist;
|
|
271
|
-
expect(msg).to.have.property('subject');
|
|
272
|
-
expect(msg).to.have.property('from');
|
|
273
|
-
done();
|
|
274
|
-
} catch (err) {
|
|
275
|
-
done(err);
|
|
276
|
-
}
|
|
277
|
-
});
|
|
278
|
-
|
|
279
|
-
// Simulate the email processing that would normally happen
|
|
280
|
-
// when the IMAP connection finds new emails
|
|
281
|
-
setTimeout(() => {
|
|
282
|
-
// This simulates what your email-receiver node does internally
|
|
283
|
-
// when it processes an email from IMAP
|
|
284
|
-
const processedEmail = {
|
|
285
|
-
payload: 'This is a mock email body for testing purposes.',
|
|
286
|
-
subject: 'Mock Email Subject',
|
|
287
|
-
from: { text: 'sender@test.com' },
|
|
288
|
-
to: { text: 'recipient@test.com' },
|
|
289
|
-
date: new Date(),
|
|
290
|
-
messageId: '<mock-message-id@test.com>',
|
|
291
|
-
};
|
|
292
|
-
|
|
293
|
-
n1.send(processedEmail);
|
|
294
|
-
}, 50);
|
|
295
|
-
} catch (err) {
|
|
296
|
-
done(err);
|
|
297
|
-
}
|
|
298
|
-
});
|
|
299
|
-
});
|
|
300
|
-
});
|
|
301
|
-
|
|
302
|
-
describe('Configuration Validation', function () {
|
|
303
|
-
it('should handle invalid configuration gracefully', function (done) {
|
|
304
|
-
// ARRANGE: Use invalid config from helpers
|
|
305
|
-
const flow = [testConfigs.invalidConfig];
|
|
306
|
-
|
|
307
|
-
// ACT: Load node with invalid config
|
|
308
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
309
|
-
try {
|
|
310
|
-
const n1 = helper.getNode(testConfigs.invalidConfig.id);
|
|
311
|
-
expect(n1).to.exist;
|
|
312
|
-
|
|
313
|
-
// ASSERT: Node should exist but handle invalid config appropriately
|
|
314
|
-
// Send input to trigger validation
|
|
315
|
-
n1.receive({ payload: 'test' });
|
|
316
|
-
|
|
317
|
-
// If we get here without crashing, the validation worked
|
|
318
|
-
testUtils.wait(300).then(() => {
|
|
319
|
-
done();
|
|
320
|
-
});
|
|
321
|
-
} catch (err) {
|
|
322
|
-
done(err);
|
|
323
|
-
}
|
|
324
|
-
});
|
|
325
|
-
});
|
|
326
|
-
|
|
327
|
-
it('should validate folder configurations properly', async function () {
|
|
328
|
-
// ARRANGE: Test different folder configurations
|
|
329
|
-
const folderConfigs = [testConfigs.valid, testConfigs.arrayFolders];
|
|
330
|
-
|
|
331
|
-
for (const config of folderConfigs) {
|
|
332
|
-
await new Promise((resolve, reject) => {
|
|
333
|
-
const flow = [config];
|
|
334
|
-
|
|
335
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
336
|
-
try {
|
|
337
|
-
const n1 = helper.getNode(config.id);
|
|
338
|
-
|
|
339
|
-
// ASSERT: Node should load successfully with different folder configs
|
|
340
|
-
expect(n1).to.exist;
|
|
341
|
-
expect(n1).to.have.property('name', config.name);
|
|
342
|
-
|
|
343
|
-
helper.unload();
|
|
344
|
-
resolve();
|
|
345
|
-
} catch (err) {
|
|
346
|
-
reject(err);
|
|
347
|
-
}
|
|
348
|
-
});
|
|
349
|
-
});
|
|
350
|
-
}
|
|
351
|
-
});
|
|
352
|
-
});
|
|
353
|
-
|
|
354
|
-
describe('Mock Integration Verification', function () {
|
|
355
|
-
it('should work with createMockImap from helpers', function (done) {
|
|
356
|
-
// ARRANGE: Create IMAP mock instance directly
|
|
357
|
-
const mockImap = createMockImap();
|
|
358
|
-
const imapInstance = new mockImap({
|
|
359
|
-
host: testConfigs.valid.host,
|
|
360
|
-
port: testConfigs.valid.port,
|
|
361
|
-
secure: true,
|
|
362
|
-
});
|
|
363
|
-
|
|
364
|
-
// ACT: Test IMAP mock behavior
|
|
365
|
-
let readyFired = false;
|
|
366
|
-
imapInstance.once('ready', () => {
|
|
367
|
-
readyFired = true;
|
|
368
|
-
|
|
369
|
-
// Test openBox functionality
|
|
370
|
-
imapInstance.openBox('INBOX', false, (err, box) => {
|
|
371
|
-
expect(err).to.not.exist;
|
|
372
|
-
expect(box).to.exist;
|
|
373
|
-
expect(box).to.have.property('messages');
|
|
374
|
-
|
|
375
|
-
// ASSERT: Mock IMAP should work as expected
|
|
376
|
-
expect(readyFired).to.be.true;
|
|
377
|
-
done();
|
|
378
|
-
});
|
|
379
|
-
});
|
|
380
|
-
|
|
381
|
-
imapInstance.connect();
|
|
382
|
-
});
|
|
383
|
-
|
|
384
|
-
it('should work with createMockMailparser from helpers', async function () {
|
|
385
|
-
// ARRANGE: Create mailparser mock instance directly
|
|
386
|
-
const mockMailparser = createMockMailparser();
|
|
387
|
-
|
|
388
|
-
// ACT: Test mailparser mock behavior
|
|
389
|
-
const result = await mockMailparser.simpleParser('test content', {
|
|
390
|
-
subject: 'Integration Test Email',
|
|
391
|
-
from: 'integration@test.com',
|
|
392
|
-
});
|
|
393
|
-
|
|
394
|
-
// ASSERT: Mock mailparser should return expected structure
|
|
395
|
-
expect(result).to.have.property('subject', 'Integration Test Email');
|
|
396
|
-
expect(result).to.have.property('from');
|
|
397
|
-
expect(result.from).to.have.property('text', 'integration@test.com');
|
|
398
|
-
expect(result).to.have.property('headers');
|
|
399
|
-
expect(result.headers).to.be.an.instanceOf(Map);
|
|
400
|
-
});
|
|
401
|
-
});
|
|
402
|
-
|
|
403
|
-
describe('Node Lifecycle', function () {
|
|
404
|
-
it('should clean up properly on unload', async function () {
|
|
405
|
-
// ARRANGE: Use test flow from helpers
|
|
406
|
-
const flow = testFlows.single;
|
|
407
|
-
|
|
408
|
-
return new Promise((resolve, reject) => {
|
|
409
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
410
|
-
try {
|
|
411
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
412
|
-
expect(n1).to.exist;
|
|
413
|
-
|
|
414
|
-
// Simulate some activity
|
|
415
|
-
n1.receive({ payload: 'test' });
|
|
416
|
-
|
|
417
|
-
// Wait a bit for any async operations
|
|
418
|
-
testUtils.wait(100).then(() => {
|
|
419
|
-
// ASSERT: Unloading should not throw errors
|
|
420
|
-
helper.unload();
|
|
421
|
-
resolve();
|
|
422
|
-
});
|
|
423
|
-
} catch (err) {
|
|
424
|
-
reject(err);
|
|
425
|
-
}
|
|
426
|
-
});
|
|
427
|
-
});
|
|
428
|
-
});
|
|
429
|
-
|
|
430
|
-
it('should handle multiple load/unload cycles', async function () {
|
|
431
|
-
// ARRANGE: Test multiple cycles
|
|
432
|
-
const flow = testFlows.single;
|
|
433
|
-
const cycles = 3;
|
|
434
|
-
|
|
435
|
-
for (let i = 0; i < cycles; i++) {
|
|
436
|
-
await new Promise((resolve, reject) => {
|
|
437
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
438
|
-
try {
|
|
439
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
440
|
-
expect(n1).to.exist;
|
|
441
|
-
|
|
442
|
-
// Quick activity simulation
|
|
443
|
-
n1.receive({ payload: `test cycle ${i}` });
|
|
444
|
-
|
|
445
|
-
testUtils.wait(50).then(() => {
|
|
446
|
-
helper.unload();
|
|
447
|
-
resolve();
|
|
448
|
-
});
|
|
449
|
-
} catch (err) {
|
|
450
|
-
reject(err);
|
|
451
|
-
}
|
|
452
|
-
});
|
|
453
|
-
});
|
|
454
|
-
}
|
|
455
|
-
|
|
456
|
-
// ASSERT: If we complete all cycles without error, lifecycle handling works
|
|
457
|
-
// This assertion is implicit in the successful completion of the loop
|
|
458
|
-
});
|
|
459
|
-
});
|
|
460
|
-
|
|
461
|
-
describe('Advanced Flow Testing', function () {
|
|
462
|
-
it('should handle complex message flows with multiple helpers', function (done) {
|
|
463
|
-
// ARRANGE: Use multi-output flow from helpers
|
|
464
|
-
const flow = testFlows.multiOutput;
|
|
465
|
-
let receivedMessages = [];
|
|
466
|
-
|
|
467
|
-
helper.load(emailReceiverNode, flow, function () {
|
|
468
|
-
try {
|
|
469
|
-
const n1 = helper.getNode(testConfigs.valid.id);
|
|
470
|
-
const h1 = helper.getNode('h1');
|
|
471
|
-
const h2 = helper.getNode('h2');
|
|
472
|
-
|
|
473
|
-
// Set up listeners for both helper nodes
|
|
474
|
-
h1.on('input', function (msg) {
|
|
475
|
-
receivedMessages.push({ node: 'h1', msg: msg });
|
|
476
|
-
checkCompletion();
|
|
477
|
-
});
|
|
478
|
-
|
|
479
|
-
h2.on('input', function (msg) {
|
|
480
|
-
receivedMessages.push({ node: 'h2', msg: msg });
|
|
481
|
-
checkCompletion();
|
|
482
|
-
});
|
|
483
|
-
|
|
484
|
-
function checkCompletion() {
|
|
485
|
-
if (receivedMessages.length >= 2) {
|
|
486
|
-
// ASSERT: Both helpers should receive messages
|
|
487
|
-
expect(receivedMessages.length).to.equal(2);
|
|
488
|
-
|
|
489
|
-
receivedMessages.forEach((item) => {
|
|
490
|
-
expect(item.msg).to.exist;
|
|
491
|
-
expect(item.msg.payload).to.exist;
|
|
492
|
-
});
|
|
493
|
-
|
|
494
|
-
done();
|
|
495
|
-
}
|
|
496
|
-
}
|
|
497
|
-
|
|
498
|
-
// Simulate email processing that sends to multiple outputs
|
|
499
|
-
setTimeout(() => {
|
|
500
|
-
const mockEmail = {
|
|
501
|
-
payload: 'This is a mock email body for testing purposes.',
|
|
502
|
-
subject: 'Multi-output Test',
|
|
503
|
-
from: { text: 'multi@test.com' },
|
|
504
|
-
};
|
|
505
|
-
|
|
506
|
-
// Send the same message to both outputs (simulating multi-output behavior)
|
|
507
|
-
n1.send([mockEmail, mockEmail]);
|
|
508
|
-
}, 50);
|
|
509
|
-
} catch (err) {
|
|
510
|
-
done(err);
|
|
511
|
-
}
|
|
512
|
-
});
|
|
513
|
-
});
|
|
514
|
-
});
|
|
515
|
-
});
|