@ti-engine/core 1.1.10 → 1.2.0

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.
@@ -78,7 +78,8 @@ class RedisClient {
78
78
  #clientIdentifier;
79
79
  #retryMaxInterval = 1000;
80
80
  #retryMaxAttempts = undefined;
81
- #redisClient = undefined;
81
+ #redisConnection = undefined;
82
+ #redisClientID;
82
83
  #serverInfo = {};
83
84
  #serverFeatures = {};
84
85
  #connectionObservers = [];
@@ -106,6 +107,17 @@ class RedisClient {
106
107
  return this.#clientIdentifier;
107
108
  }
108
109
 
110
+ /**
111
+ * Used to return the Redis client ID.
112
+ *
113
+ * @property
114
+ * @returns {number}
115
+ * @public
116
+ */
117
+ get clientID() {
118
+ return this.#redisClientID;
119
+ }
120
+
109
121
  /**
110
122
  * Used to return the Redis server version.
111
123
  *
@@ -144,73 +156,27 @@ class RedisClient {
144
156
  */
145
157
  initialize( host, port, authKey, user, defaultDB, retryMaxIntervalMs = 1000, retryMaxAttempts = undefined ) {
146
158
  return new Promise( ( resolve, reject ) => {
147
- if ( this.#redisClient ) {
159
+ if ( this.#redisConnection ) {
148
160
  resolve();
149
161
  } else {
150
- try {
151
- this.#retryMaxInterval = retryMaxIntervalMs;
152
- this.#retryMaxAttempts = retryMaxAttempts;
153
-
154
- let retryStrategy = ( attempt ) => {
155
- let result = Math.min( attempt * 50, this.#retryMaxInterval );
156
-
157
- if ( this.#retryMaxAttempts != null && attempt > this.#retryMaxAttempts ) {
158
- logger.log( "In Redis retry strategy: reached max attempts for command retry. Aborting...", logger.logSeverity.WARNING, { attempts: attempt } );
159
- result = exceptions.raise( exceptions.exceptionCode.E_COM_RETRY_ATTEMPTS_EXCEEDED );
160
- }
161
-
162
- return result;
163
- };
164
-
165
- let reconnectOnError = ( error ) => {
166
- logger.log( `In Redis reconnect on error strategy: ${ error.message }`, logger.logSeverity.ERROR, error );
167
- return !!error.message.includes( "READONLY" );
168
- };
169
-
170
- let options = {
171
- port: port,
172
- host: host,
173
- username: user,
174
- password: authKey,
175
- db: defaultDB,
176
- autoResendUnfulfilledCommands: true,
177
- maxRetriesPerRequest: null,
178
- retryStrategy: retryStrategy,
179
- reconnectOnError: reconnectOnError
180
- };
181
-
182
- /** @type Redis */
183
- this.#redisClient = new Redis( options );
184
-
185
- this.#redisClient.on( "ready", () => {
186
- logger.log( `Connection to Redis server ${ host }:${ port } (re)established by client '${ this.identifier }' and is ready to be used.`, logger.logSeverity.INFO );
187
-
188
- // Notify all connection observers about this event:
189
- _.forEach( this.#connectionObservers, ( connectionObservers ) => {
190
- connectionObservers.onConnectionRecovered( this.#clientIdentifier );
191
- } );
192
-
193
- // Fetch the server information and store it:
194
- this.#fetchServerInfo();
195
-
196
- resolve();
162
+ this.#setupClient( host, port, authKey, user, defaultDB, retryMaxIntervalMs, retryMaxAttempts ).then( () => {
163
+ // Fetch the server information and store it:
164
+ return this.#fetchServerInfo();
165
+ } ).then( () => {
166
+ return this.#getClientId();
167
+ } ).then( ( clientID ) => {
168
+ // Store the client ID:
169
+ this.#redisClientID = clientID;
170
+
171
+ // Notify all connection observers about the initialization success:
172
+ _.forEach( this.#connectionObservers, ( connectionObservers ) => {
173
+ connectionObservers.onConnectionRecovered( this.#clientIdentifier );
197
174
  } );
198
- this.#redisClient.on( "error", ( error ) => {
199
- logger.log( `Error received in Redis client '${ this.identifier }'.`, logger.logSeverity.ERROR, error );
200
175
 
201
- // Notify all connection observers about this event:
202
- _.forEach( this.#connectionObservers, ( connectionObservers ) => {
203
- connectionObservers.onConnectionDisrupted( this.#clientIdentifier );
204
- } );
205
- } );
206
- this.#redisClient.on( "reconnecting", ( info ) => {
207
- if ( info.attempt > 1 ) {
208
- logger.log( `Client '${ this.identifier }' reconnecting to Redis server after ${ info.delay } ms. This is attempt ${ info.attempt }.`, logger.logSeverity.DEBUG );
209
- }
210
- } );
211
- } catch ( error ) {
176
+ resolve();
177
+ } ).catch( ( error ) => {
212
178
  reject( exceptions.raise( error ) );
213
- }
179
+ } );
214
180
  }
215
181
  } );
216
182
  }
@@ -240,7 +206,7 @@ class RedisClient {
240
206
  */
241
207
  executeCommands( commands ) {
242
208
  return new Promise( ( resolve, reject ) => {
243
- this.#redisClient.multi( commands ).exec().then( ( results ) => {
209
+ this.#redisConnection.multi( commands ).exec().then( ( results ) => {
244
210
  resolve( results );
245
211
  } ).catch( ( error ) => {
246
212
  reject( exceptions.raise( error ) );
@@ -261,7 +227,7 @@ class RedisClient {
261
227
  */
262
228
  blockingCommand( command, commandArguments ) {
263
229
  return new Promise( ( resolve, reject ) => {
264
- this.#redisClient[ command ].apply( this.#redisClient, commandArguments ).then( ( results ) => {
230
+ this.#redisConnection[ command ].apply( this.#redisConnection, commandArguments ).then( ( results ) => {
265
231
  resolve( results );
266
232
  } ).catch( ( error ) => {
267
233
  reject( exceptions.raise( error ) );
@@ -280,7 +246,7 @@ class RedisClient {
280
246
  */
281
247
  publishCommand( channel, message ) {
282
248
  return new Promise( ( resolve, reject ) => {
283
- this.#redisClient.publish( channel, tools.stringifyJSON( message ) ).then( ( receivedBy ) => {
249
+ this.#redisConnection.publish( channel, tools.stringifyJSON( message ) ).then( ( receivedBy ) => {
284
250
  resolve( receivedBy );
285
251
  } ).catch( ( error ) => {
286
252
  reject( exceptions.raise( error ) );
@@ -301,7 +267,7 @@ class RedisClient {
301
267
  */
302
268
  subscribeCommand( channel, messageHandler ) {
303
269
  return new Promise( ( resolve, reject ) => {
304
- // Avoid attaching multiple listeners for the same channel:
270
+ // Avoid attaching multiple listeners to the same channel:
305
271
  if ( this.#messageHandlersByChannel.has( channel ) ) {
306
272
  logger.log( "Attempting to subscribe to message channel '" + channel + "' while already subscribed to it.", logger.logSeverity.WARNING );
307
273
  resolve();
@@ -312,21 +278,21 @@ class RedisClient {
312
278
  }
313
279
  };
314
280
 
315
- this.#redisClient.once( "subscribe", ( subscribedChannel ) => {
281
+ this.#redisConnection.once( "subscribe", ( subscribedChannel ) => {
316
282
  if ( subscribedChannel === channel ) {
317
283
  logger.log( "Subscription to message channel '" + channel + "' successful.", logger.logSeverity.DEBUG );
318
284
  resolve();
319
285
  }
320
286
  } );
321
287
 
322
- this.#redisClient.on( "message", onMessage );
288
+ this.#redisConnection.on( "message", onMessage );
323
289
  this.#messageHandlersByChannel.set( channel, onMessage );
324
290
 
325
- this.#redisClient.subscribe( channel ).catch( ( error ) => {
291
+ this.#redisConnection.subscribe( channel ).catch( ( error ) => {
326
292
  // Cleanup partial state if subscribe fails:
327
293
  const handler = this.#messageHandlersByChannel.get( channel );
328
294
  if ( handler ) {
329
- this.#redisClient.off( "message", handler );
295
+ this.#redisConnection.off( "message", handler );
330
296
  this.#messageHandlersByChannel.delete( channel );
331
297
  }
332
298
  reject( exceptions.raise( error ) );
@@ -347,10 +313,11 @@ class RedisClient {
347
313
  return new Promise( ( resolve, reject ) => {
348
314
  const handler = this.#messageHandlersByChannel.get( channel );
349
315
  if ( handler ) {
350
- this.#redisClient.off( "message", handler );
316
+ this.#redisConnection.off( "message", handler );
351
317
  this.#messageHandlersByChannel.delete( channel );
352
318
  }
353
- this.#redisClient.unsubscribe( channel ).then( () => {
319
+
320
+ this.#redisConnection.unsubscribe( channel ).then( () => {
354
321
  resolve();
355
322
  } ).catch( ( error ) => {
356
323
  reject( exceptions.raise( error ) );
@@ -372,7 +339,7 @@ class RedisClient {
372
339
  */
373
340
  callCommand( commandArguments ) {
374
341
  return new Promise( ( resolve, reject ) => {
375
- this.#redisClient[ "call" ].apply( this.#redisClient, commandArguments ).then( ( result ) => {
342
+ this.#redisConnection[ "call" ].apply( this.#redisConnection, commandArguments ).then( ( result ) => {
376
343
  resolve( result );
377
344
  } ).catch( ( error ) => {
378
345
  reject( exceptions.raise( error ) );
@@ -386,7 +353,7 @@ class RedisClient {
386
353
  *
387
354
  * @method
388
355
  * @param {number} [timeoutMs=1000]
389
- * @returns {Promise<Object>}
356
+ * @returns {Promise}
390
357
  * @public
391
358
  */
392
359
  shutDown( timeoutMs = 1000 ) {
@@ -401,19 +368,19 @@ class RedisClient {
401
368
 
402
369
  const timeout = setTimeout( () => {
403
370
  try {
404
- this.#redisClient.disconnect();
371
+ this.#redisConnection.disconnect();
405
372
  } catch ( error ) {
406
373
  }
407
374
  done();
408
375
  }, timeoutMs );
409
376
 
410
- this.#redisClient.quit().then( () => {
377
+ this.#redisConnection.quit().then( () => {
411
378
  clearTimeout( timeout );
412
379
  done();
413
380
  } ).catch( () => {
414
381
  clearTimeout( timeout );
415
382
  try {
416
- this.#redisClient.disconnect();
383
+ this.#redisConnection.disconnect();
417
384
  } catch ( error ) {
418
385
  }
419
386
  done();
@@ -424,40 +391,131 @@ class RedisClient {
424
391
  /* Private interface */
425
392
 
426
393
  /**
427
- * Used to fetch and store Redis server information.
394
+ * Used to set up the connection to Redis server.
395
+ * <br/>
396
+ * NOTE: This method will only resolve once the server sends a 'ready' event.
428
397
  *
429
398
  * @method
430
- * @private
399
+ * @param {string} host
400
+ * @param {number} port
401
+ * @param {string} authKey
402
+ * @param {string} user
403
+ * @param {number} defaultDB
404
+ * @param {number} [retryMaxIntervalMs=1000] Optional max backoff interval.
405
+ * @param {number|undefined} [retryMaxAttempts=undefined] Optional max (re)connection attempts before abort.
406
+ * @public
431
407
  */
432
- #fetchServerInfo() {
433
- this.#redisClient.info().then( ( result ) => {
434
- this.#serverInfo = {};
435
- if ( _.isString( result ) ) {
436
- let rawData = _.split( result, "\r\n" );
437
- _.forEach( rawData, ( entry ) => {
438
- let details = _.split( entry, ":" );
439
- if ( !_.startsWith( details[ 0 ], "#" ) && details[ 0 ] !== "" && details[ 0 ] ) {
440
- if ( _.isNaN( _.toNumber( details[ 1 ] ) ) ) {
441
- this.#serverInfo[ details[ 0 ] ] = details[ 1 ];
442
- } else {
443
- this.#serverInfo[ details[ 0 ] ] = _.toNumber( details[ 1 ] );
444
- }
408
+ #setupClient( host, port, authKey, user, defaultDB, retryMaxIntervalMs, retryMaxAttempts ) {
409
+ return new Promise( ( resolve, reject ) => {
410
+ try {
411
+ this.#retryMaxInterval = retryMaxIntervalMs;
412
+ this.#retryMaxAttempts = retryMaxAttempts;
413
+
414
+ let retryStrategy = ( attempt ) => {
415
+ let result = Math.min( attempt * 50, this.#retryMaxInterval );
416
+
417
+ if ( this.#retryMaxAttempts != null && attempt > this.#retryMaxAttempts ) {
418
+ logger.log( "In Redis retry strategy: reached max attempts for command retry. Aborting...", logger.logSeverity.WARNING, { attempts: attempt } );
419
+ result = exceptions.raise( exceptions.exceptionCode.E_COM_RETRY_ATTEMPTS_EXCEEDED );
445
420
  }
421
+
422
+ return result;
423
+ };
424
+
425
+ let reconnectOnError = ( error ) => {
426
+ logger.log( `In Redis reconnect on error strategy: ${ error.message }`, logger.logSeverity.ERROR, error );
427
+ return !!error.message.includes( "READONLY" );
428
+ };
429
+
430
+ let options = {
431
+ port: port,
432
+ host: host,
433
+ username: user,
434
+ password: authKey,
435
+ db: defaultDB,
436
+ autoResendUnfulfilledCommands: true,
437
+ maxRetriesPerRequest: null,
438
+ retryStrategy: retryStrategy,
439
+ reconnectOnError: reconnectOnError
440
+ };
441
+
442
+ /** @type Redis */
443
+ this.#redisConnection = new Redis( options );
444
+
445
+ this.#redisConnection.on( "ready", () => {
446
+ logger.log( `Connection to Redis server ${ host }:${ port } (re)established by client '${ this.identifier }' and is ready to be used.`, logger.logSeverity.INFO );
447
+ resolve();
446
448
  } );
447
- }
448
- return this.#redisClient.module( "LIST" );
449
- } ).then( ( result ) => {
450
- this.#serverFeatures = {};
451
- if ( _.isArray( result ) ) {
452
- _.forEach( result, ( entry ) => {
453
- this.#serverFeatures[ entry[ 1 ] ] = entry[ 3 ];
449
+ this.#redisConnection.on( "error", ( error ) => {
450
+ logger.log( `Error received in Redis client '${ this.identifier }'.`, logger.logSeverity.ERROR, error );
451
+
452
+ // Notify all connection observers about this event:
453
+ _.forEach( this.#connectionObservers, ( connectionObservers ) => {
454
+ connectionObservers.onConnectionDisrupted( this.#clientIdentifier );
455
+ } );
456
+ } );
457
+ this.#redisConnection.on( "reconnecting", ( info ) => {
458
+ if ( info.attempt > 1 ) {
459
+ logger.log( `Client '${ this.identifier }' reconnecting to Redis server after ${ info.delay } ms. This is attempt ${ info.attempt }.`, logger.logSeverity.DEBUG );
460
+ }
454
461
  } );
462
+ } catch ( error ) {
463
+ reject( exceptions.raise( error ) );
455
464
  }
456
- } ).catch( ( error ) => {
457
- logger.log( `Failed to fetch server information by client '${ this.identifier }'!`, logger.logSeverity.WARNING, error );
458
465
  } );
459
466
  }
460
467
 
468
+ /**
469
+ * Used to fetch and store Redis server information.
470
+ *
471
+ * @method
472
+ * @private
473
+ */
474
+ #fetchServerInfo() {
475
+ return new Promise( ( resolve, reject ) => {
476
+ this.#redisConnection.info().then( ( result ) => {
477
+ this.#serverInfo = {};
478
+ if ( _.isString( result ) ) {
479
+ let rawData = _.split( result, "\r\n" );
480
+ _.forEach( rawData, ( entry ) => {
481
+ let details = _.split( entry, ":" );
482
+ if ( !_.startsWith( details[ 0 ], "#" ) && details[ 0 ] !== "" && details[ 0 ] ) {
483
+ if ( _.isNaN( _.toNumber( details[ 1 ] ) ) ) {
484
+ this.#serverInfo[ details[ 0 ] ] = details[ 1 ];
485
+ } else {
486
+ this.#serverInfo[ details[ 0 ] ] = _.toNumber( details[ 1 ] );
487
+ }
488
+ }
489
+ } );
490
+ }
491
+ return this.#redisConnection.module( "LIST" );
492
+ } ).then( ( result ) => {
493
+ this.#serverFeatures = {};
494
+ if ( _.isArray( result ) ) {
495
+ _.forEach( result, ( entry ) => {
496
+ this.#serverFeatures[ entry[ 1 ] ] = entry[ 3 ];
497
+ } );
498
+ }
499
+ resolve();
500
+ } ).catch( ( error ) => {
501
+ logger.log( `Failed to fetch Redis server information by client '${ this.identifier }'!`, logger.logSeverity.WARNING, error );
502
+ reject( exceptions.raise( error ) );
503
+ } );
504
+ } );
505
+ }
506
+
507
+ /**
508
+ * Used to fetch and store the Redis client ID.
509
+ *
510
+ * @method
511
+ * @returns {Promise<number>}
512
+ * @private
513
+ */
514
+ #getClientId() {
515
+ let commandArguments = [ "client", "id" ];
516
+ return this.callCommand( commandArguments ).then( ( clientID ) => Number( clientID ) );
517
+ }
518
+
461
519
  }
462
520
 
463
521
  /**
package/package.json CHANGED
@@ -1,64 +1,66 @@
1
- {
2
- "name": "@ti-engine/core",
3
- "version": "1.1.10",
4
- "description": "The ti-engine is an open source, free to use—both for personal and commercial projects—framework for the creation of microservice-based solutions using node.js.",
5
- "author": "Boris Kostadinov <kostadinov.boris@gmail.com>",
6
- "license": "GPL-3.0-or-later",
7
- "exports": {
8
- "./exceptions": "./utils/exceptions.js",
9
- "./localization": "./utils/localization.js",
10
- "./logger": "./utils/logger.js",
11
- "./service-consumer": "./components/service-consumer.js",
12
- "./service-instance": "./components/service-instance.js",
13
- "./service-provider": "./components/service-provider.js",
14
- "./tools": "./utils/tools.js"
15
- },
16
- "imports": {
17
- "#auditing": "./components/auditing.js",
18
- "#cache": "./utils/cache.js",
19
- "#config": "./utils/config.js",
20
- "#connection-observer": "./components/connection-observer.js",
21
- "#default-message-exchange": "./components/exchange/default/default-message-exchange.js",
22
- "#default-message-receiver": "./components/exchange/default/default-message-receiver.js",
23
- "#default-message-sender": "./components/exchange/default/default-message-sender.js",
24
- "#exceptions": "./utils/exceptions.js",
25
- "#gcloud-integration": "./integrations/gcloud-integration.js",
26
- "#localization": "./utils/localization.js",
27
- "#logger": "./utils/logger.js",
28
- "#message-dispatcher": "./components/exchange/message-dispatcher.js",
29
- "#message-exchange": "./components/exchange/message-exchange.js",
30
- "#message-handler": "./components/exchange/message-handler.js",
31
- "#message-memory-cache": "./components/exchange/message-memory-cache.js",
32
- "#message-observer": "./components/exchange/message-observer.js",
33
- "#message-receiver": "./components/exchange/message-receiver.js",
34
- "#message-sender": "./components/exchange/message-sender.js",
35
- "#message-tracer": "./components/exchange/message-tracer.js",
36
- "#redis-integration": "./integrations/redis-integration.js",
37
- "#service-caller": "./components/service-caller.js",
38
- "#service-consumer": "./components/service-consumer.js",
39
- "#service-executor": "./components/service-executor.js",
40
- "#service-instance": "./components/service-instance.js",
41
- "#service-provider": "./components/service-provider.js",
42
- "#settings": "./bin/settings.json",
43
- "#tools": "./utils/tools.js"
44
- },
45
- "dependencies": {
46
- "blake2": "^5.0.0",
47
- "dotenv": "^17.2.1",
48
- "fs-extra": "^11.3.1",
49
- "lodash": "^4.17.21",
50
- "node-schedule": "^2.1.1",
51
- "ioredis": "^5.7.0"
52
- },
53
- "optionalDependencies": {
54
- "@google-cloud/error-reporting": "^3.0.5",
55
- "zeromq": "^6.5.0"
56
- },
57
- "repository": {
58
- "type": "git",
59
- "url": "git+https://github.com/Belleal/ti-engine.git"
60
- },
61
- "engines": {
62
- "node": ">=14.17.0"
63
- }
1
+ {
2
+ "name": "@ti-engine/core",
3
+ "version": "1.2.0",
4
+ "description": "The ti-engine is an open source, free to use—both for personal and commercial projects—framework for the creation of microservice-based solutions using node.js.",
5
+ "author": "Boris Kostadinov <kostadinov.boris@gmail.com>",
6
+ "license": "GPL-3.0-or-later",
7
+ "exports": {
8
+ ".": "./bin/start-instance.js",
9
+ "./exceptions": "./utils/exceptions.js",
10
+ "./localization": "./utils/localization.js",
11
+ "./logger": "./utils/logger.js",
12
+ "./service-consumer": "./components/service-consumer.js",
13
+ "./service-instance": "./components/service-instance.js",
14
+ "./service-provider": "./components/service-provider.js",
15
+ "./tools": "./utils/tools.js"
16
+ },
17
+ "imports": {
18
+ "#auditing": "./components/auditing.js",
19
+ "#cache": "./utils/cache.js",
20
+ "#config": "./utils/config.js",
21
+ "#connection-observer": "./components/connection-observer.js",
22
+ "#default-message-exchange": "./components/exchange/default/default-message-exchange.js",
23
+ "#default-message-receiver": "./components/exchange/default/default-message-receiver.js",
24
+ "#default-message-sender": "./components/exchange/default/default-message-sender.js",
25
+ "#exceptions": "./utils/exceptions.js",
26
+ "#gcloud-integration": "./integrations/gcloud-integration.js",
27
+ "#labels": "./bin/localization/labels.json",
28
+ "#localization": "./utils/localization.js",
29
+ "#logger": "./utils/logger.js",
30
+ "#message-dispatcher": "./components/exchange/message-dispatcher.js",
31
+ "#message-exchange": "./components/exchange/message-exchange.js",
32
+ "#message-handler": "./components/exchange/message-handler.js",
33
+ "#message-memory-cache": "./components/exchange/message-memory-cache.js",
34
+ "#message-observer": "./components/exchange/message-observer.js",
35
+ "#message-receiver": "./components/exchange/message-receiver.js",
36
+ "#message-sender": "./components/exchange/message-sender.js",
37
+ "#message-tracer": "./components/exchange/message-tracer.js",
38
+ "#redis-integration": "./integrations/redis-integration.js",
39
+ "#service-caller": "./components/service-caller.js",
40
+ "#service-consumer": "./components/service-consumer.js",
41
+ "#service-executor": "./components/service-executor.js",
42
+ "#service-instance": "./components/service-instance.js",
43
+ "#service-provider": "./components/service-provider.js",
44
+ "#settings": "./bin/settings.json",
45
+ "#tools": "./utils/tools.js"
46
+ },
47
+ "dependencies": {
48
+ "blake2": "^5.0.0",
49
+ "dotenv": "^17.2.1",
50
+ "fs-extra": "^11.3.1",
51
+ "lodash": "^4.17.21",
52
+ "node-schedule": "^2.1.1",
53
+ "ioredis": "^5.7.0"
54
+ },
55
+ "optionalDependencies": {
56
+ "@google-cloud/error-reporting": "^3.0.5",
57
+ "zeromq": "^6.5.0"
58
+ },
59
+ "repository": {
60
+ "type": "git",
61
+ "url": "git+https://github.com/Belleal/ti-engine.git"
62
+ },
63
+ "engines": {
64
+ "node": ">=14.17.0"
65
+ }
64
66
  }
package/utils/config.js CHANGED
@@ -72,7 +72,7 @@ const tools = require( "#tools" );
72
72
 
73
73
  /**
74
74
  * @typedef {Object} SettingsLocalization
75
- * @property {string} labelsPath
75
+ * @property {Array<string>} labelsPath
76
76
  * @property {string} language
77
77
  */
78
78
 
@@ -200,4 +200,4 @@ Object.freeze( settings );
200
200
  */
201
201
  module.exports.getSetting = ( setting, defaultValue ) => {
202
202
  return _.get( settings, setting, defaultValue );
203
- };
203
+ };
@@ -37,6 +37,7 @@ let exceptionCodeEnum = tools.enum( {
37
37
  E_COM_SERVICE_NOT_REGISTERED: [ 3003, "service not registered", "The specified service is not found in the service registry." ],
38
38
  E_COM_SERVICE_NOT_FOUND: [ 3004, "service not found", "The specified service is not found in the service definition interface." ],
39
39
  E_COM_SERVICE_HANDLER_NOT_FOUND: [ 3005, "service handler not found", "No handler found in the interface for the specified service or service version." ],
40
+ E_COM_MESSAGE_RECEIVER_UNAVAILABLE: [ 3006, "message receiver unavailable", "The message receiver instance is currently unavailable." ],
40
41
  // E_COM_UNRECOGNIZED_API_URL: [ 301, "unrecognized api url", "Attempt to access unrecognized or invalid API URL." ],
41
42
  // E_COM_MISSING_REQUIRED_ARGUMENTS: [ 302, "missing required arguments", "Attempt to execute operation without all required arguments." ],
42
43
  // E_COM_UNRECOGNIZED_RESPONSE_STRUCTURE: [ 303, "unrecognized response structure", "The received response has unrecognized structure and cannot be parsed or examined." ],
@@ -1,30 +1,33 @@
1
- /*
2
- * The ti-engine is an open source, free to use—both for personal and commercial projects—framework for the creation of microservice-based solutions using node.js.
3
- * Copyright © 2021-2025 Boris Kostadinov <kostadinov.boris@gmail.com>
4
- * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
5
- * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
6
- * You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
7
- */
8
-
9
- const _ = require( "lodash" );
10
- const path = require( "path" );
11
- const config = require( "#config" );
12
-
13
- const labelsPath = path.normalize( path.join( process.cwd(), config.getSetting( config.setting.LOCALIZATION_LABELS_PATH ) ) );
14
- const labels = require( labelsPath );
15
- const defaultEmptyLabel = "!!! label not found !!!";
16
-
17
- // prevent further modifications to the labels object:
18
- Object.freeze( labels );
19
-
20
- /**
21
- * Used to return the textual value for a label based on the current system language.
22
- *
23
- * @method
24
- * @param {string} label This should be a dot-separated JSON path string.
25
- * @returns {string}
26
- * @public
27
- */
28
- module.exports.getLabel = ( label ) => {
29
- return _.get( labels, label + "." + config.getSetting( config.setting.LOCALIZATION_LANGUAGE ), defaultEmptyLabel );
1
+ /*
2
+ * The ti-engine is an open source, free to use—both for personal and commercial projects—framework for the creation of microservice-based solutions using node.js.
3
+ * Copyright © 2021-2025 Boris Kostadinov <kostadinov.boris@gmail.com>
4
+ * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
5
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
6
+ * You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
7
+ */
8
+
9
+ const _ = require( "lodash" );
10
+ const path = require( "path" );
11
+ const config = require( "#config" );
12
+
13
+ // const labelsPath = path.normalize( path.join( process.cwd(), config.getSetting( config.setting.LOCALIZATION_LABELS_PATH ) ) );
14
+ // const labels = require( labelsPath );
15
+ const labels = require( "#labels" );
16
+ const defaultEmptyLabel = "!!! label not found !!!";
17
+
18
+ // TODO: Add functionality to import additional custom labels.
19
+
20
+ // prevent further modifications to the labels object:
21
+ Object.freeze( labels );
22
+
23
+ /**
24
+ * Used to return the textual value for a label based on the current system language.
25
+ *
26
+ * @method
27
+ * @param {string} label This should be a dot-separated JSON path string.
28
+ * @returns {string}
29
+ * @public
30
+ */
31
+ module.exports.getLabel = ( label ) => {
32
+ return _.get( labels, label + "." + config.getSetting( config.setting.LOCALIZATION_LANGUAGE ), defaultEmptyLabel );
30
33
  };
package/testRedis.js DELETED
@@ -1,22 +0,0 @@
1
- import Redis from "ioredis";
2
-
3
- const redisClient = new Redis( {
4
- port: 17467,
5
- host: "redis-17467.c300.eu-central-1-1.ec2.redns.redis-cloud.com",
6
- username: "default",
7
- password: "o49Iyj2JYnmD7NSFWa32x2iYqulWkIM1",
8
- db: 0,
9
- autoResendUnfulfilledCommands: true,
10
- maxRetriesPerRequest: null,
11
- retryStrategy: ( attempt ) => {
12
- let result = Math.min( attempt * 50, 1000 );
13
- }
14
- });
15
-
16
- redisClient.on('error', err => console.log('Redis Client Error', err));
17
-
18
- //await redisClient.connect();
19
-
20
- await redisClient.set('foo', 'bar');
21
- const result = await redisClient.get('foo');
22
- console.log(result);