mqtt-devices-parser 1.0.22 → 1.0.24
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/Changelog.md +29 -0
- package/index.js +2 -2
- package/models/devices.models.js +10 -0
- package/models/mqtt.models.js +14 -0
- package/models/mqttTemplate.models.js +8 -0
- package/models/sensors.models.js +4 -0
- package/package.json +1 -1
- package/src/db/device.js +115 -19
- package/src/device/device.js +136 -4
- package/src/kafka/consumer.js +10 -2
package/Changelog.md
CHANGED
|
@@ -1,5 +1,34 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 1.0.24
|
|
4
|
+
src/device/device: fix log
|
|
5
|
+
src/kafka/consumer: increase initialRetryTime from 100 to 300ms
|
|
6
|
+
src/device/device: parseMqttMessage: get remote configs if not known
|
|
7
|
+
synch configs if they mismatch
|
|
8
|
+
models/devices.models: new column synch
|
|
9
|
+
synchs mqtt topics
|
|
10
|
+
Explanation
|
|
11
|
+
**
|
|
12
|
+
When a message is received, it checks if mqtt topic is associated to the device without "set" if present.
|
|
13
|
+
If topic exists and ends with set, updates localData column. If topic exists and doesn't end with set, updates remoteData column.
|
|
14
|
+
If localData was updated sets topic as unsynched
|
|
15
|
+
If remoteData was received and differs from localData and synch is enabled, tries to synch topic
|
|
16
|
+
**
|
|
17
|
+
adds synch and synched columns to mqtt table
|
|
18
|
+
Adds methods getMqttTopic, updateRemoteTopic, setSynchedTopic
|
|
19
|
+
kafka: adds random number to kafka when program is in dev mode.
|
|
20
|
+
Avoids to read all queue messages since last session
|
|
21
|
+
mqtt templates: preparing mqtt topics synch
|
|
22
|
+
new column synch and localData for mqttTemplates table
|
|
23
|
+
new column mqttTemplate_id for mqtt table
|
|
24
|
+
add property "property" to table sensors
|
|
25
|
+
src/device/device: decode json payload and get property associated
|
|
26
|
+
models/devices: add synched column (for future implementations)
|
|
27
|
+
|
|
28
|
+
## 1.0.23
|
|
29
|
+
src/device/device: fix tech, version and app_version db update
|
|
30
|
+
npm warn audit Updating websocket-stream to 5.3.0, which is a SemVer major change.
|
|
31
|
+
|
|
3
32
|
## 1.0.22
|
|
4
33
|
Adds SSL and SASL support for kafka
|
|
5
34
|
mqtt.parseMessages removed
|
package/index.js
CHANGED
|
@@ -174,7 +174,7 @@ function mqtt_connect(){
|
|
|
174
174
|
$.mqtt_client.subscribe(project+"/#", (err) => {
|
|
175
175
|
if(err){
|
|
176
176
|
console.log("[MQTT] error");
|
|
177
|
-
console.
|
|
177
|
+
console.error(err);
|
|
178
178
|
}
|
|
179
179
|
else
|
|
180
180
|
console.log("[MQTT] subscribed to project:",project);
|
|
@@ -230,6 +230,6 @@ function mqtt_connect(){
|
|
|
230
230
|
|
|
231
231
|
$.mqtt_client.on("error",(error)=>{
|
|
232
232
|
console.log("[MQTT] error");
|
|
233
|
-
console.
|
|
233
|
+
console.error(error)
|
|
234
234
|
})
|
|
235
235
|
}
|
package/models/devices.models.js
CHANGED
|
@@ -71,6 +71,16 @@ module.exports = (sequelize,DataTypes)=>{
|
|
|
71
71
|
type: DataTypes.STRING,
|
|
72
72
|
allowNull: true
|
|
73
73
|
},
|
|
74
|
+
synch: { // set to 1 to enable auto synch
|
|
75
|
+
type: DataTypes.INTEGER,
|
|
76
|
+
default: 0,
|
|
77
|
+
allowNull: true
|
|
78
|
+
},
|
|
79
|
+
synched: { // handle internally
|
|
80
|
+
type: DataTypes.INTEGER,
|
|
81
|
+
default: 0,
|
|
82
|
+
allowNull: true
|
|
83
|
+
},
|
|
74
84
|
},
|
|
75
85
|
{
|
|
76
86
|
tableName: 'devices',
|
package/models/mqtt.models.js
CHANGED
|
@@ -32,6 +32,20 @@ module.exports = (sequelize,DataTypes)=>{
|
|
|
32
32
|
template_id: {
|
|
33
33
|
type: DataTypes.INTEGER,
|
|
34
34
|
allowNull: true,
|
|
35
|
+
},
|
|
36
|
+
mqttTemplate_id: {
|
|
37
|
+
type: DataTypes.INTEGER,
|
|
38
|
+
allowNull: true,
|
|
39
|
+
},
|
|
40
|
+
synch: {
|
|
41
|
+
type: DataTypes.INTEGER,
|
|
42
|
+
default: 0,
|
|
43
|
+
allowNull: true,
|
|
44
|
+
},
|
|
45
|
+
synched: {
|
|
46
|
+
type: DataTypes.INTEGER,
|
|
47
|
+
default: 0,
|
|
48
|
+
allowNull: true,
|
|
35
49
|
}
|
|
36
50
|
},
|
|
37
51
|
{
|
|
@@ -13,10 +13,18 @@ module.exports = (sequelize,DataTypes)=>{
|
|
|
13
13
|
type: DataTypes.JSON,
|
|
14
14
|
allowNull: true
|
|
15
15
|
},
|
|
16
|
+
localData: {
|
|
17
|
+
type: DataTypes.JSON,
|
|
18
|
+
allowNull: true
|
|
19
|
+
},
|
|
16
20
|
readInterval: {
|
|
17
21
|
type: DataTypes.INTEGER,
|
|
18
22
|
allowNull: true
|
|
19
23
|
},
|
|
24
|
+
synch: {
|
|
25
|
+
type: DataTypes.INTEGER,
|
|
26
|
+
allowNull: true
|
|
27
|
+
},
|
|
20
28
|
template_id: {
|
|
21
29
|
type: DataTypes.INTEGER,
|
|
22
30
|
allowNull: false
|
package/models/sensors.models.js
CHANGED
package/package.json
CHANGED
package/src/db/device.js
CHANGED
|
@@ -194,7 +194,6 @@ var self = module.exports = {
|
|
|
194
194
|
});
|
|
195
195
|
},
|
|
196
196
|
|
|
197
|
-
|
|
198
197
|
addLog : async(id,column,value)=>{
|
|
199
198
|
return new Promise((resolve,reject) => {
|
|
200
199
|
|
|
@@ -255,26 +254,26 @@ var self = module.exports = {
|
|
|
255
254
|
|
|
256
255
|
getLocalSettings : async(deviceId)=>{
|
|
257
256
|
|
|
258
|
-
|
|
257
|
+
return new Promise((resolve,reject) => {
|
|
259
258
|
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
259
|
+
let query = "SELECT local_settings FROM ?? where id = ?";
|
|
260
|
+
let table = ["devices", deviceId];
|
|
261
|
+
query = mysql.format(query,table);
|
|
263
262
|
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
263
|
+
$.db.queryRow(query)
|
|
264
|
+
.then( rows => {
|
|
265
|
+
if(rows?.length > 0)
|
|
266
|
+
return resolve(rows[0]?.local_settings);
|
|
267
|
+
else
|
|
268
|
+
return resolve(null);
|
|
269
|
+
})
|
|
270
|
+
.catch( err => {
|
|
271
|
+
return reject(err);
|
|
272
|
+
});
|
|
274
273
|
});
|
|
275
|
-
|
|
274
|
+
},
|
|
276
275
|
|
|
277
|
-
|
|
276
|
+
updateLocalSettings : async(settings, deviceId)=>{
|
|
278
277
|
|
|
279
278
|
return new Promise((resolve,reject) => {
|
|
280
279
|
let obj = {
|
|
@@ -299,7 +298,7 @@ var self = module.exports = {
|
|
|
299
298
|
});
|
|
300
299
|
},
|
|
301
300
|
|
|
302
|
-
|
|
301
|
+
getRemoteSettings : async(deviceId)=>{
|
|
303
302
|
|
|
304
303
|
return new Promise((resolve,reject) => {
|
|
305
304
|
|
|
@@ -408,6 +407,103 @@ var self = module.exports = {
|
|
|
408
407
|
return resolve(null);
|
|
409
408
|
});
|
|
410
409
|
});
|
|
411
|
-
}
|
|
410
|
+
},
|
|
411
|
+
|
|
412
|
+
getMqttTopic : async(deviceId, topic)=>{
|
|
413
|
+
return new Promise((resolve,reject) => {
|
|
414
|
+
|
|
415
|
+
let query = "SELECT * FROM ?? where device_id = ? and topic = ?";
|
|
416
|
+
let args = ["mqtt",deviceId,topic];
|
|
417
|
+
query = mysql.format(query,args);
|
|
418
|
+
|
|
419
|
+
$.db.queryRow(query)
|
|
420
|
+
.then( rows => {
|
|
421
|
+
if(rows.length > 0)
|
|
422
|
+
return resolve(rows[0]);
|
|
423
|
+
else
|
|
424
|
+
return resolve(null);
|
|
425
|
+
})
|
|
426
|
+
.catch( err => {
|
|
427
|
+
console.log(err);
|
|
428
|
+
return resolve(null);
|
|
429
|
+
});
|
|
430
|
+
});
|
|
431
|
+
},
|
|
412
432
|
|
|
433
|
+
updateLocalTopic : async(id, data)=>{
|
|
434
|
+
|
|
435
|
+
let jsonData = {
|
|
436
|
+
value : data
|
|
437
|
+
};
|
|
438
|
+
|
|
439
|
+
return new Promise((resolve,reject) => {
|
|
440
|
+
let obj = {
|
|
441
|
+
localData : JSON.stringify(jsonData),
|
|
442
|
+
updatedAt : moment().utc().format('YYYY-MM-DD HH:mm:ss')
|
|
443
|
+
}
|
|
444
|
+
|
|
445
|
+
let filter = {
|
|
446
|
+
id
|
|
447
|
+
};
|
|
448
|
+
|
|
449
|
+
$.db.update("mqtt",obj,filter)
|
|
450
|
+
.then (rows => {
|
|
451
|
+
return resolve(rows[0]);
|
|
452
|
+
})
|
|
453
|
+
.catch(error => {
|
|
454
|
+
return reject(error);
|
|
455
|
+
});
|
|
456
|
+
|
|
457
|
+
});
|
|
458
|
+
},
|
|
459
|
+
|
|
460
|
+
updateRemoteTopic : async(id, data)=>{
|
|
461
|
+
|
|
462
|
+
let jsonData = {
|
|
463
|
+
value : data
|
|
464
|
+
};
|
|
465
|
+
|
|
466
|
+
return new Promise((resolve,reject) => {
|
|
467
|
+
let obj = {
|
|
468
|
+
remoteData : JSON.stringify(jsonData),
|
|
469
|
+
updatedAt : moment().utc().format('YYYY-MM-DD HH:mm:ss')
|
|
470
|
+
}
|
|
471
|
+
|
|
472
|
+
let filter = {
|
|
473
|
+
id
|
|
474
|
+
};
|
|
475
|
+
|
|
476
|
+
$.db.update("mqtt",obj,filter)
|
|
477
|
+
.then (rows => {
|
|
478
|
+
return resolve(rows[0]);
|
|
479
|
+
})
|
|
480
|
+
.catch(error => {
|
|
481
|
+
return reject(error);
|
|
482
|
+
});
|
|
483
|
+
|
|
484
|
+
});
|
|
485
|
+
},
|
|
486
|
+
|
|
487
|
+
setSynchedTopic : async(id, data)=>{
|
|
488
|
+
|
|
489
|
+
return new Promise((resolve,reject) => {
|
|
490
|
+
let obj = {
|
|
491
|
+
synched : data ? 1 : 0,
|
|
492
|
+
updatedAt : moment().utc().format('YYYY-MM-DD HH:mm:ss')
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
let filter = {
|
|
496
|
+
id,
|
|
497
|
+
};
|
|
498
|
+
|
|
499
|
+
$.db.update("mqtt",obj,filter)
|
|
500
|
+
.then (rows => {
|
|
501
|
+
return resolve(rows[0]);
|
|
502
|
+
})
|
|
503
|
+
.catch(error => {
|
|
504
|
+
return reject(error);
|
|
505
|
+
});
|
|
506
|
+
|
|
507
|
+
});
|
|
508
|
+
},
|
|
413
509
|
}
|
package/src/device/device.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
const moment = require('moment');
|
|
2
|
+
const { isDeepStrictEqual } = require('node:util');
|
|
2
3
|
|
|
3
4
|
var _project = [];
|
|
4
5
|
const logs_table = "logs_sensor";
|
|
@@ -281,6 +282,7 @@ async function parseMqttMessage(client, project_name, device, topic, payload, re
|
|
|
281
282
|
if(topic.endsWith("/get"))
|
|
282
283
|
return;
|
|
283
284
|
|
|
285
|
+
const topicBck = topic;
|
|
284
286
|
//console.log("[MQTT] parse topic: ",topic);
|
|
285
287
|
|
|
286
288
|
try{
|
|
@@ -296,6 +298,31 @@ async function parseMqttMessage(client, project_name, device, topic, payload, re
|
|
|
296
298
|
$.db_device.update(device.id, "status", payload);
|
|
297
299
|
$.db_device.addLog(device.id,"status",payload);
|
|
298
300
|
}
|
|
301
|
+
|
|
302
|
+
if (payload === "online"){
|
|
303
|
+
let mqtt_prefix = `${project_name}/${device.uid}`;
|
|
304
|
+
// check if remote settings are known, if not require it
|
|
305
|
+
if(!device.remote_settings?.log){
|
|
306
|
+
let topic = `${mqtt_prefix}/settings/log/get`
|
|
307
|
+
$.mqtt_client.publish(topic,"",{qos:1,retain:false});
|
|
308
|
+
}
|
|
309
|
+
if(!device.remote_settings?.keepalive){
|
|
310
|
+
let topic = `${mqtt_prefix}/settings/keepalive/get`
|
|
311
|
+
$.mqtt_client.publish(topic,"",{qos:1,retain:false});
|
|
312
|
+
}
|
|
313
|
+
if(!device.remote_settings?.modem){
|
|
314
|
+
let topic = `${mqtt_prefix}/settings/modem/get`
|
|
315
|
+
$.mqtt_client.publish(topic,"",{qos:1,retain:false});
|
|
316
|
+
}
|
|
317
|
+
if(!device.remote_settings?.wifi){
|
|
318
|
+
let topic = `${mqtt_prefix}/settings/wifi/get`
|
|
319
|
+
$.mqtt_client.publish(topic,"",{qos:1,retain:false});
|
|
320
|
+
}
|
|
321
|
+
if(!device.remote_settings?.mqtt){
|
|
322
|
+
let topic = `${mqtt_prefix}/settings/mqtt/get`
|
|
323
|
+
$.mqtt_client.publish(topic,"",{qos:1,retain:false});
|
|
324
|
+
}
|
|
325
|
+
}
|
|
299
326
|
return;
|
|
300
327
|
break;
|
|
301
328
|
case "model":
|
|
@@ -308,14 +335,14 @@ async function parseMqttMessage(client, project_name, device, topic, payload, re
|
|
|
308
335
|
return;
|
|
309
336
|
break;
|
|
310
337
|
case "tech":
|
|
311
|
-
if (
|
|
338
|
+
if (payload != null && payload != device?.tech) {
|
|
312
339
|
$.db_device.update(device.id, "tech", payload);
|
|
313
340
|
$.db_device.addLog(device.id,"tech",payload);
|
|
314
341
|
}
|
|
315
342
|
return;
|
|
316
343
|
break;
|
|
317
344
|
case "version":
|
|
318
|
-
if (
|
|
345
|
+
if (payload != null && payload != device?.version) {
|
|
319
346
|
$.db_device.addLog(device.id,"version",payload);
|
|
320
347
|
$.db_device.update(device.id, "version", payload);
|
|
321
348
|
handleFotaSuccess(device.id);
|
|
@@ -323,7 +350,7 @@ async function parseMqttMessage(client, project_name, device, topic, payload, re
|
|
|
323
350
|
return;
|
|
324
351
|
break;
|
|
325
352
|
case "app_version":
|
|
326
|
-
if (
|
|
353
|
+
if (payload != null && payload != device?.app_version) {
|
|
327
354
|
$.db_device.addLog(device.id,"app_version",payload);
|
|
328
355
|
$.db_device.update(device.id, "app_version", payload);
|
|
329
356
|
handleFotaSuccess(device.id);
|
|
@@ -370,6 +397,45 @@ async function parseMqttMessage(client, project_name, device, topic, payload, re
|
|
|
370
397
|
// Optional: default case if needed
|
|
371
398
|
default:
|
|
372
399
|
// handle other topics or do nothing
|
|
400
|
+
// check if topic is associated with device
|
|
401
|
+
let findTopic = topicBck;
|
|
402
|
+
if(topicBck.endsWith("/set")) // remove set if exists on topic
|
|
403
|
+
findTopic = getWordBeforeLastSlash(topicBck);
|
|
404
|
+
|
|
405
|
+
const dbTopic = await $.db_device.getMqttTopic(device.id,findTopic)
|
|
406
|
+
if(dbTopic != null){
|
|
407
|
+
if(topicBck.endsWith("/set")){
|
|
408
|
+
// update local topic
|
|
409
|
+
$.db_device.updateLocalTopic(dbTopic.id,payload)
|
|
410
|
+
.then(()=>{
|
|
411
|
+
// set as not synched
|
|
412
|
+
$.db_device.setSynchedTopic(dbTopic.id,false);
|
|
413
|
+
})
|
|
414
|
+
.catch((error)=>{
|
|
415
|
+
console.error(error);
|
|
416
|
+
})
|
|
417
|
+
}else{
|
|
418
|
+
// update remote topic
|
|
419
|
+
$.db_device.updateRemoteTopic(dbTopic.id,payload)
|
|
420
|
+
.then(async (res)=>{
|
|
421
|
+
// check if topics mismatch
|
|
422
|
+
if(isDeepStrictEqual(dbTopic?.localData, dbTopic?.remoteData)){
|
|
423
|
+
$.db_device.setSynchedTopic(dbTopic.id,true);
|
|
424
|
+
}else{
|
|
425
|
+
// set as not synched
|
|
426
|
+
await $.db_device.setSynchedTopic(dbTopic.id,false);
|
|
427
|
+
if(dbTopic?.synch){ // check if sync is enabled
|
|
428
|
+
// synch topic
|
|
429
|
+
synchMqttTopic(device,dbTopic,findTopic);
|
|
430
|
+
}
|
|
431
|
+
}
|
|
432
|
+
})
|
|
433
|
+
.catch((error)=>{
|
|
434
|
+
console.error(error);
|
|
435
|
+
})
|
|
436
|
+
|
|
437
|
+
}
|
|
438
|
+
}
|
|
373
439
|
break;
|
|
374
440
|
}
|
|
375
441
|
|
|
@@ -378,7 +444,26 @@ async function parseMqttMessage(client, project_name, device, topic, payload, re
|
|
|
378
444
|
}
|
|
379
445
|
}
|
|
380
446
|
|
|
381
|
-
async function
|
|
447
|
+
async function synchMqttTopic(device,dbTopic,topicBck){
|
|
448
|
+
|
|
449
|
+
const project = await $.db_project.getById(device.project_id);
|
|
450
|
+
let mqtt_prefix = `${project.name}/${device.uid}`;
|
|
451
|
+
let topic = `${mqtt_prefix}/${topicBck}/set`
|
|
452
|
+
let payload = "";
|
|
453
|
+
if(dbTopic?.remoteData && typeof dbTopic?.remoteData === 'object'){
|
|
454
|
+
try{
|
|
455
|
+
payload = JSON.stringify(dbTopic?.remoteData);
|
|
456
|
+
}catch(err){
|
|
457
|
+
console.error(err);
|
|
458
|
+
return;
|
|
459
|
+
}
|
|
460
|
+
}else{
|
|
461
|
+
payload = dbTopic?.remoteData;
|
|
462
|
+
}
|
|
463
|
+
$.mqtt_client.publish(topic,payload,{qos:1,retain:false});
|
|
464
|
+
}
|
|
465
|
+
|
|
466
|
+
async function updateLocalSettings(device,topic,payload){
|
|
382
467
|
|
|
383
468
|
$.db_device.addLog(device.id,"local_settings",JSON.stringify(payload));
|
|
384
469
|
|
|
@@ -469,11 +554,41 @@ async function updateRemoteSettings(device,topic,payload){
|
|
|
469
554
|
|
|
470
555
|
try {
|
|
471
556
|
await $.db_device.updateRemoteSettings(JSON.stringify(settings), device.id);
|
|
557
|
+
if(device?.synch)
|
|
558
|
+
synchSettings(device,route[0]);
|
|
472
559
|
} catch (err) {
|
|
473
560
|
console.error("Failed to update local settings:", err);
|
|
474
561
|
}
|
|
475
562
|
}
|
|
476
563
|
|
|
564
|
+
async function synchSettings(device,key){
|
|
565
|
+
|
|
566
|
+
console.log(`check topic ${key} from ${device.uid}`);
|
|
567
|
+
// Retrieve existing settings
|
|
568
|
+
let localSettings = await $.db_device.getLocalSettings(device.id);
|
|
569
|
+
console.log(localSettings)
|
|
570
|
+
let remoteSettings = await $.db_device.getRemoteSettings(device.id);
|
|
571
|
+
console.log(remoteSettings)
|
|
572
|
+
|
|
573
|
+
//let keys = await checkSettings(localSettings,remoteSettings);
|
|
574
|
+
if(localSettings?.hasOwnProperty(key) && remoteSettings?.hasOwnProperty(key)){
|
|
575
|
+
if(!isDeepStrictEqual(localSettings?.[key], remoteSettings?.[key])){
|
|
576
|
+
const project = await $.db_project.getById(device.project_id);
|
|
577
|
+
let mqtt_prefix = `${project.name}/${device.uid}`;
|
|
578
|
+
let topic = `${mqtt_prefix}/settings/${key}/set`
|
|
579
|
+
try{
|
|
580
|
+
const payload = JSON.stringify(localSettings[key]);
|
|
581
|
+
console.log(`updating key: ${key} with data:`);
|
|
582
|
+
console.log(payload);
|
|
583
|
+
$.mqtt_client.publish(topic,payload,{qos:1,retain:false});
|
|
584
|
+
}catch(err){
|
|
585
|
+
console.error(localSettings[key])
|
|
586
|
+
console.error(err);
|
|
587
|
+
}
|
|
588
|
+
}
|
|
589
|
+
}
|
|
590
|
+
}
|
|
591
|
+
|
|
477
592
|
async function updateSensor(device,ref,payload){
|
|
478
593
|
let res = await $.db_device.getSensorByRef(device.id,ref)
|
|
479
594
|
if(res == null)
|
|
@@ -486,6 +601,14 @@ async function updateSensor(device,ref,payload){
|
|
|
486
601
|
error = null;
|
|
487
602
|
timestamp = null;
|
|
488
603
|
|
|
604
|
+
if(res?.type.toLowerCase() === "json"){
|
|
605
|
+
if(res?.property && payload.hasOwnProperty(res?.property)){
|
|
606
|
+
object = payload[res.property];
|
|
607
|
+
}else{
|
|
608
|
+
return;
|
|
609
|
+
}
|
|
610
|
+
}
|
|
611
|
+
|
|
489
612
|
if (typeof object === 'object' && object !== null) {
|
|
490
613
|
value = object?.value || object?.v;
|
|
491
614
|
error = object?.error || object?.e;
|
|
@@ -553,3 +676,12 @@ function getWordAfterLastSlash(str){
|
|
|
553
676
|
}
|
|
554
677
|
return str.substring(lastSlashIndex + 1);
|
|
555
678
|
}
|
|
679
|
+
|
|
680
|
+
function getWordBeforeLastSlash(str){
|
|
681
|
+
const lastSlashIndex = str.lastIndexOf('/');
|
|
682
|
+
if (lastSlashIndex === -1) {
|
|
683
|
+
// No slash found, return the original string
|
|
684
|
+
return str;
|
|
685
|
+
}
|
|
686
|
+
return str.substring(0,lastSlashIndex);
|
|
687
|
+
}
|
package/src/kafka/consumer.js
CHANGED
|
@@ -58,9 +58,17 @@ var self = module.exports = {
|
|
|
58
58
|
|
|
59
59
|
kafka = new Kafka(kafkaConfig);
|
|
60
60
|
|
|
61
|
+
let kafkaGroupId = "";
|
|
62
|
+
if(config.env === 'development'){
|
|
63
|
+
const n = Math.floor(Math.random() * 1000) + 1; // 1..1000
|
|
64
|
+
kafkaGroupId = `${config.kafka.groupId}-${String(n)}`;
|
|
65
|
+
}else{
|
|
66
|
+
kafkaGroupId = config.kafka.groupId;
|
|
67
|
+
}
|
|
68
|
+
|
|
61
69
|
// Create consumer with shared subscription support
|
|
62
70
|
consumer = kafka.consumer({
|
|
63
|
-
groupId:
|
|
71
|
+
groupId: kafkaGroupId,
|
|
64
72
|
sessionTimeout: 30000,
|
|
65
73
|
rebalanceTimeout: 60000,
|
|
66
74
|
heartbeatInterval: 3000,
|
|
@@ -69,7 +77,7 @@ var self = module.exports = {
|
|
|
69
77
|
maxBytes: 10485760,
|
|
70
78
|
maxWaitTimeInMs: 5000,
|
|
71
79
|
retry: {
|
|
72
|
-
initialRetryTime:
|
|
80
|
+
initialRetryTime: 300,
|
|
73
81
|
retries: 8
|
|
74
82
|
}
|
|
75
83
|
});
|