queclink-parser 1.9.13 → 1.9.15
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 +33 -0
- package/example.js +31 -32
- package/package.json +1 -1
- package/src/gv310lau.js +117 -212
- package/src/gv57cg.js +4 -4
- package/src/gv58lau.js +94 -257
- package/src/index.js +8 -1
- package/src/messages/es.json +11 -11
- package/src/utils.js +300 -13
package/src/utils.js
CHANGED
|
@@ -211,13 +211,24 @@ const bluetoothModels = {
|
|
|
211
211
|
'0': 'MAG ELA (Door Sensor)'
|
|
212
212
|
},
|
|
213
213
|
'12': {
|
|
214
|
-
'0': '
|
|
214
|
+
'0': 'ATP100/ATP102'
|
|
215
215
|
},
|
|
216
216
|
'13': {
|
|
217
217
|
'0': 'WRL300 (Bluetooth Relay)'
|
|
218
218
|
}
|
|
219
219
|
}
|
|
220
220
|
|
|
221
|
+
/*
|
|
222
|
+
BLE Temp & Hum sensors
|
|
223
|
+
*/
|
|
224
|
+
const bleTempHumSensors = {
|
|
225
|
+
'AC100': '0',
|
|
226
|
+
'WTH300': '2',
|
|
227
|
+
'RHT ELA': '3',
|
|
228
|
+
'WMS301': '4',
|
|
229
|
+
'WTH301': '5'
|
|
230
|
+
}
|
|
231
|
+
|
|
221
232
|
/*
|
|
222
233
|
Possible Beacon ID Models
|
|
223
234
|
*/
|
|
@@ -234,7 +245,19 @@ const beaconModels = {
|
|
|
234
245
|
const beaconTypes = {
|
|
235
246
|
'0': 'ID',
|
|
236
247
|
'1': 'iBeacon',
|
|
237
|
-
'2': 'Eddystone'
|
|
248
|
+
'2': 'Eddystone',
|
|
249
|
+
'3': 'Queclink'
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
/*
|
|
253
|
+
Possible Relay BLE config results
|
|
254
|
+
*/
|
|
255
|
+
const relayBLEResults = {
|
|
256
|
+
0: 'Success',
|
|
257
|
+
1: 'Error connecting',
|
|
258
|
+
2: 'Incorrect BLE password',
|
|
259
|
+
3: 'Error updating BLE password',
|
|
260
|
+
4: 'Error'
|
|
238
261
|
}
|
|
239
262
|
|
|
240
263
|
/*
|
|
@@ -408,12 +431,46 @@ const getTempInCelciousDegrees = hexTemp => {
|
|
|
408
431
|
}
|
|
409
432
|
|
|
410
433
|
/*
|
|
411
|
-
Gets the temperature
|
|
434
|
+
Gets the temperature from BLE devices in celcious degrees
|
|
435
|
+
*/
|
|
436
|
+
const getBleTempInCelciousDegrees = (device, hexData) => {
|
|
437
|
+
if (device === 'WTH300') {
|
|
438
|
+
let intTemp = parseInt(hexData.substring(0, 2), 16)
|
|
439
|
+
let decTemp = parseInt(hexData.substring(2, 4), 16)
|
|
440
|
+
return intTemp + decTemp / 256
|
|
441
|
+
} else if (['WTH301', 'WMS301'].includes(device)) {
|
|
442
|
+
let intTemp = parseInt(hexData.substring(0, 2), 16)
|
|
443
|
+
let decTemp = parseInt(hexData.substring(2, 4), 16)
|
|
444
|
+
return intTemp + decTemp / 100
|
|
445
|
+
} else if (device === 'ATP100/ATP102') {
|
|
446
|
+
let temp = parseInt(hexData.substring(4, 6), 16)
|
|
447
|
+
return temp - 40
|
|
448
|
+
} else {
|
|
449
|
+
return null
|
|
450
|
+
}
|
|
451
|
+
}
|
|
452
|
+
|
|
453
|
+
/*
|
|
454
|
+
Gets the humidity from BLE devices in rh
|
|
412
455
|
*/
|
|
413
|
-
const
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
456
|
+
const getBleHumidityInRH = (device, hexData) => {
|
|
457
|
+
let intHum = parseInt(hexData.substring(4, 6), 16)
|
|
458
|
+
let decHum = parseInt(hexData.substring(6, 8), 16)
|
|
459
|
+
if (device === 'WTH300') {
|
|
460
|
+
return intHum + decHum / 256
|
|
461
|
+
} else if (['WTH301', 'WMS301'].includes(device)) {
|
|
462
|
+
return intHum + decHum / 100
|
|
463
|
+
} else {
|
|
464
|
+
return null
|
|
465
|
+
}
|
|
466
|
+
}
|
|
467
|
+
|
|
468
|
+
/*
|
|
469
|
+
Gets the humidity from BLE devices in rh
|
|
470
|
+
*/
|
|
471
|
+
const getTirePressureInPSI = hexData => {
|
|
472
|
+
let tirePress = parseInt(hexData.substring(2, 4), 16) * 2.5 // In kPa
|
|
473
|
+
return tirePress / 6.895 // In PSI
|
|
417
474
|
}
|
|
418
475
|
|
|
419
476
|
/*
|
|
@@ -851,14 +908,14 @@ const getCanData = (parsedData, ix) => {
|
|
|
851
908
|
? expansionBin[2] === '1'
|
|
852
909
|
: null,
|
|
853
910
|
batteryIndicator: expansionBin ? expansionBin[3] === '1' : null,
|
|
854
|
-
|
|
911
|
+
brakeSystemFailureIndicator: expansionBin
|
|
855
912
|
? expansionBin[4] === '1'
|
|
856
913
|
: null,
|
|
857
914
|
oilPressureIndicator: expansionBin ? expansionBin[5] === '1' : null,
|
|
858
915
|
engineHotIndicator: expansionBin ? expansionBin[6] === '1' : null,
|
|
859
916
|
ABSFailureIndicator: expansionBin ? expansionBin[7] === '1' : null,
|
|
860
917
|
checkEngineIndicator: expansionBin ? expansionBin[9] === '1' : null,
|
|
861
|
-
|
|
918
|
+
airbagsIndicator: expansionBin ? expansionBin[10] === '1' : null,
|
|
862
919
|
serviceCallIndicator: expansionBin
|
|
863
920
|
? expansionBin[11] === '1'
|
|
864
921
|
: null,
|
|
@@ -871,6 +928,177 @@ const getCanData = (parsedData, ix) => {
|
|
|
871
928
|
}
|
|
872
929
|
}
|
|
873
930
|
|
|
931
|
+
|
|
932
|
+
/*
|
|
933
|
+
Get Bluetooth data
|
|
934
|
+
*/
|
|
935
|
+
const getBleData = (parsedData, btIndex) => {
|
|
936
|
+
let btDevices = []
|
|
937
|
+
let cnt = btIndex + 1
|
|
938
|
+
let btNum = parsedData[btIndex] !== '' ? parseInt(parsedData[btIndex]) : 1
|
|
939
|
+
|
|
940
|
+
for (let c = 0; c < btNum; c++) {
|
|
941
|
+
if (!['FE', 'FF'].includes(parsedData[cnt])) {
|
|
942
|
+
let appendMask = nHexDigit(hex2bin(parsedData[cnt + 4]), 16)
|
|
943
|
+
let aNameIx = cnt + 4 + parseInt(appendMask[15])
|
|
944
|
+
let aMacIx = aNameIx + parseInt(appendMask[14])
|
|
945
|
+
let aStatIx = aMacIx + parseInt(appendMask[13])
|
|
946
|
+
let aBatIx = aStatIx + parseInt(appendMask[12])
|
|
947
|
+
let aTmpIx = aBatIx + parseInt(appendMask[11])
|
|
948
|
+
let aHumIx = aTmpIx + parseInt(appendMask[10])
|
|
949
|
+
let ioIx = aHumIx + parseInt(appendMask[8])
|
|
950
|
+
let aEvIx = appendMask[8] === '1' && appendMask[7] === '1'
|
|
951
|
+
? ioIx + 3 : ioIx + parseInt(appendMask[7])
|
|
952
|
+
let pressIx = appendMask[7] === '1' && appendMask[6] === '1'
|
|
953
|
+
? aEvIx + 2 : aEvIx + parseInt(appendMask[6])
|
|
954
|
+
let timeIx = pressIx + parseInt(appendMask[5])
|
|
955
|
+
let eTmpIx = timeIx + parseInt(appendMask[4])
|
|
956
|
+
let magIx = eTmpIx + parseInt(appendMask[3])
|
|
957
|
+
let aBatpIx = appendMask[3] === '1' && appendMask[2] === '1'
|
|
958
|
+
? magIx + 3 : magIx + parseInt(appendMask[2])
|
|
959
|
+
let relIx = aBatpIx + parseInt(appendMask[1])
|
|
960
|
+
|
|
961
|
+
let bleType = bluetoothAccessories[parsedData[cnt + 1]]
|
|
962
|
+
let bleModel = parsedData[cnt + 2] !== ''
|
|
963
|
+
? bluetoothModels[parsedData[cnt + 1]][parsedData[cnt + 2]]
|
|
964
|
+
: null
|
|
965
|
+
let rawAppendMask = parsedData[cnt + 4]
|
|
966
|
+
|
|
967
|
+
btDevices.push({
|
|
968
|
+
index: parsedData[cnt],
|
|
969
|
+
type: bleType,
|
|
970
|
+
model: bleModel,
|
|
971
|
+
appendMask: rawAppendMask,
|
|
972
|
+
name:
|
|
973
|
+
parsedData[aNameIx] !== '' && appendMask[15] === '1'
|
|
974
|
+
? parsedData[aNameIx]
|
|
975
|
+
: null,
|
|
976
|
+
mac:
|
|
977
|
+
parsedData[aMacIx] !== '' && appendMask[14] === '1'
|
|
978
|
+
? parsedData[aMacIx]
|
|
979
|
+
: null,
|
|
980
|
+
status:
|
|
981
|
+
parsedData[aStatIx] !== '' && appendMask[13] === '1'
|
|
982
|
+
? parseInt(parsedData[aStatIx])
|
|
983
|
+
: null,
|
|
984
|
+
batteryLevel:
|
|
985
|
+
parsedData[aBatIx] !== '' && appendMask[12] === '1'
|
|
986
|
+
? parseInt(parsedData[aBatIx])
|
|
987
|
+
: null,
|
|
988
|
+
batteryPercentage:
|
|
989
|
+
parsedData[aBatpIx] !== '' && appendMask[2] === '1'
|
|
990
|
+
? parseFloat(parsedData[aBatpIx])
|
|
991
|
+
: null,
|
|
992
|
+
accessoryData: {
|
|
993
|
+
data: parsedData[cnt + 3] !== '' ? {
|
|
994
|
+
raw: parsedData[cnt + 3],
|
|
995
|
+
temperature: getBleTempInCelciousDegrees(bleModel, parsedData[cnt + 3]),
|
|
996
|
+
humidity: getBleHumidityInRH(bleModel, parsedData[cnt + 3]),
|
|
997
|
+
relayState: bleModel === 'WRL300' ? parseInt(parsedData[cnt + 3]) === 1 ? 'Connected' : 'Disconnected' : null,
|
|
998
|
+
tirePresure: getTirePressureInPSI(parsedData[cnt + 3]),
|
|
999
|
+
productModel: bleModel === 'ATP100/ATP102' ? parsedData[cnt + 3].substring(6, 7) : null,
|
|
1000
|
+
fwVersion: bleModel === 'ATP100/ATP102' ? parsedData[cnt + 3].substring(7, 8) : null,
|
|
1001
|
+
} : null,
|
|
1002
|
+
temperature:
|
|
1003
|
+
parsedData[aTmpIx] !== '' && appendMask[11] === '1'
|
|
1004
|
+
? parseInt(parsedData[aTmpIx])
|
|
1005
|
+
: null,
|
|
1006
|
+
humidity:
|
|
1007
|
+
parsedData[aHumIx] !== '' && appendMask[10] === '1'
|
|
1008
|
+
? parseInt(parsedData[aHumIx])
|
|
1009
|
+
: null,
|
|
1010
|
+
outputStatus:
|
|
1011
|
+
parsedData[ioIx] !== '' && appendMask[8] === '1'
|
|
1012
|
+
? parsedData[ioIx]
|
|
1013
|
+
: null,
|
|
1014
|
+
inputStatus:
|
|
1015
|
+
parsedData[ioIx + 1] !== '' && appendMask[8] === '1'
|
|
1016
|
+
? parsedData[ioIx + 1]
|
|
1017
|
+
: null,
|
|
1018
|
+
analogInputStatus:
|
|
1019
|
+
parsedData[ioIx + 2] !== '' && appendMask[8] === '1'
|
|
1020
|
+
? parsedData[ioIx + 2]
|
|
1021
|
+
: null,
|
|
1022
|
+
event:
|
|
1023
|
+
parsedData[aEvIx] !== '' && appendMask[7] === '1'
|
|
1024
|
+
? parseInt(parsedData[aEvIx])
|
|
1025
|
+
: null,
|
|
1026
|
+
tirePresure:
|
|
1027
|
+
parsedData[pressIx] !== '' && appendMask[6] === '1'
|
|
1028
|
+
? parseInt(parsedData[pressIx]) / 6.895
|
|
1029
|
+
: null,
|
|
1030
|
+
timestamp:
|
|
1031
|
+
parsedData[timeIx] !== '' && appendMask[5] === '1'
|
|
1032
|
+
? parseDate(parsedData[timeIx])
|
|
1033
|
+
: null,
|
|
1034
|
+
enhancedTemperature:
|
|
1035
|
+
parsedData[eTmpIx] !== '' && appendMask[4] === '1'
|
|
1036
|
+
? parseFloat(parsedData[eTmpIx])
|
|
1037
|
+
: null,
|
|
1038
|
+
magDevice: {
|
|
1039
|
+
id:
|
|
1040
|
+
parsedData[magIx] !== '' && appendMask[3] === '1'
|
|
1041
|
+
? parsedData[magIx]
|
|
1042
|
+
: null,
|
|
1043
|
+
eventCounter:
|
|
1044
|
+
parsedData[magIx + 1] !== '' && appendMask[3] === '1'
|
|
1045
|
+
? parseInt(parsedData[magIx + 1])
|
|
1046
|
+
: null,
|
|
1047
|
+
magnetState:
|
|
1048
|
+
parsedData[magIx + 2] !== '' && appendMask[3] === '1'
|
|
1049
|
+
? parseInt(parsedData[magIx + 2])
|
|
1050
|
+
: null
|
|
1051
|
+
},
|
|
1052
|
+
relay: {
|
|
1053
|
+
state:
|
|
1054
|
+
parsedData[relIx] !== '' && appendMask[1] === '1'
|
|
1055
|
+
? parseInt(parsedData[relIx])
|
|
1056
|
+
: null
|
|
1057
|
+
}
|
|
1058
|
+
}
|
|
1059
|
+
})
|
|
1060
|
+
cnt = relIx + 1
|
|
1061
|
+
} else {
|
|
1062
|
+
let appendMask = nHexDigit(hex2bin(parsedData[cnt + 3]), 8)
|
|
1063
|
+
let aMacIx = cnt + 3 + parseInt(appendMask[6])
|
|
1064
|
+
let aBatIx = aMacIx + parseInt(appendMask[4])
|
|
1065
|
+
let aSigIx = aBatIx + parseInt(appendMask[1])
|
|
1066
|
+
let bTypeIx = aSigIx + parseInt(appendMask[0])
|
|
1067
|
+
|
|
1068
|
+
btDevices.push({
|
|
1069
|
+
index: parsedData[cnt],
|
|
1070
|
+
type: beaconTypes[parsedData[cnt + 1]],
|
|
1071
|
+
model: parsedData[cnt + 2] !== ''
|
|
1072
|
+
? beaconModels[parsedData[cnt + 2]]
|
|
1073
|
+
: null,
|
|
1074
|
+
appendMask: parsedData[cnt + 3],
|
|
1075
|
+
mac:
|
|
1076
|
+
parsedData[aMacIx] !== '' && appendMask[6] === '1'
|
|
1077
|
+
? parsedData[aMacIx]
|
|
1078
|
+
: null,
|
|
1079
|
+
batteryLevel:
|
|
1080
|
+
parsedData[aBatIx] !== '' && appendMask[4] === '1'
|
|
1081
|
+
? parseInt(parsedData[aBatIx])
|
|
1082
|
+
: null,
|
|
1083
|
+
SignalStrength:
|
|
1084
|
+
parsedData[aSigIx] !== '' && appendMask[1] === '1'
|
|
1085
|
+
? parseInt(parsedData[aSigIx])
|
|
1086
|
+
: null,
|
|
1087
|
+
beaconType:
|
|
1088
|
+
parsedData[bTypeIx] !== '' && appendMask[0] === '1'
|
|
1089
|
+
? parseInt(parsedData[bTypeIx])
|
|
1090
|
+
: null,
|
|
1091
|
+
beaconData:
|
|
1092
|
+
parsedData[bTypeIx + 1] !== '' && appendMask[0] === '1'
|
|
1093
|
+
? parseInt(parsedData[bTypeIx + 1])
|
|
1094
|
+
: null,
|
|
1095
|
+
})
|
|
1096
|
+
cnt = bTypeIx + 1 + parseInt(appendMask[1])
|
|
1097
|
+
}
|
|
1098
|
+
}
|
|
1099
|
+
return btDevices
|
|
1100
|
+
}
|
|
1101
|
+
|
|
874
1102
|
/*
|
|
875
1103
|
Gets the alarm type
|
|
876
1104
|
*/
|
|
@@ -1375,10 +1603,67 @@ const getAlarm = (command, report, extra = false) => {
|
|
|
1375
1603
|
} else if (command === 'GTBDS') {
|
|
1376
1604
|
return { type: 'Bluetooth_Disonnected', message: messages[command] }
|
|
1377
1605
|
} else if (command === 'GTBAA') {
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1606
|
+
if (['01', '02', '03'].includes(report)) {
|
|
1607
|
+
const number = parseInt(extra[0])
|
|
1608
|
+
const mac = extra[1]
|
|
1609
|
+
const temperature = extra[2].enhancedTemperature ? extra[2].enhancedTemperature : extra[2].temperature
|
|
1610
|
+
const status = report !== '03' // 01 & 02 means outside range, 03 means inside range
|
|
1611
|
+
return {
|
|
1612
|
+
type: 'Outside_Temperature',
|
|
1613
|
+
number: number,
|
|
1614
|
+
deviceID: mac,
|
|
1615
|
+
status: status,
|
|
1616
|
+
temperature: temperature,
|
|
1617
|
+
message: messages[command][report].replace('()', `(${temperature}°C)`)
|
|
1618
|
+
}
|
|
1619
|
+
} else if (['07', '08', '09'].includes(report)) {
|
|
1620
|
+
const number = parseInt(extra[0])
|
|
1621
|
+
const mac = extra[1]
|
|
1622
|
+
const humidity = extra[2].humidity ? extra[2].humidity : null
|
|
1623
|
+
const status = report !== '09' // 07 & 08 means outside range, 09 means inside range
|
|
1624
|
+
return {
|
|
1625
|
+
type: 'Outside_Humidity',
|
|
1626
|
+
number: number,
|
|
1627
|
+
deviceID: mac,
|
|
1628
|
+
status: status,
|
|
1629
|
+
humidity: humidity,
|
|
1630
|
+
message: messages[command][report].replace('()', `(${humidity}%)`)
|
|
1631
|
+
}
|
|
1632
|
+
} else if (['0E', '0F', '10'].includes(report)) {
|
|
1633
|
+
const number = parseInt(extra[0])
|
|
1634
|
+
const mac = extra[1]
|
|
1635
|
+
const pressure = extra[2].tirePresure ? extra[2].tirePresure : null
|
|
1636
|
+
const status = report !== '10' // 0E & 0F means outside range, 10 means inside range
|
|
1637
|
+
return {
|
|
1638
|
+
type: 'Outside_Tire_Pressure',
|
|
1639
|
+
number: number,
|
|
1640
|
+
deviceID: mac,
|
|
1641
|
+
status: status,
|
|
1642
|
+
pressure: pressure,
|
|
1643
|
+
message: messages[command][report].replace('()', `(${pressure}kPa)`)
|
|
1644
|
+
}
|
|
1645
|
+
} else if (report === '15') {
|
|
1646
|
+
const number = parseInt(extra[0])
|
|
1647
|
+
const mac = extra[1]
|
|
1648
|
+
const status = extra[2].relay.state === 1
|
|
1649
|
+
const humanStatus = status ? 'activado' : 'desactivado'
|
|
1650
|
+
const configResult = extra[2].relay.configResult ? extra[2].relay.configResult : null
|
|
1651
|
+
return {
|
|
1652
|
+
type: 'Relay_BLE',
|
|
1653
|
+
number: number,
|
|
1654
|
+
deviceID: mac,
|
|
1655
|
+
status: status,
|
|
1656
|
+
configResult: configResult,
|
|
1657
|
+
message: messages[command][report].replace('__', `${humanStatus}`)
|
|
1658
|
+
}
|
|
1659
|
+
} else {
|
|
1660
|
+
return {
|
|
1661
|
+
type: 'Bluetooth_Alarm',
|
|
1662
|
+
message: messages[command][report]
|
|
1663
|
+
}
|
|
1381
1664
|
}
|
|
1665
|
+
|
|
1666
|
+
|
|
1382
1667
|
} else {
|
|
1383
1668
|
return {
|
|
1384
1669
|
type: command,
|
|
@@ -1505,8 +1790,10 @@ module.exports = {
|
|
|
1505
1790
|
disconnectionReasons: disconnectionReasons,
|
|
1506
1791
|
bluetoothAccessories: bluetoothAccessories,
|
|
1507
1792
|
bluetoothModels: bluetoothModels,
|
|
1793
|
+
bleTempHumSensors: bleTempHumSensors,
|
|
1508
1794
|
beaconModels: beaconModels,
|
|
1509
1795
|
beaconTypes: beaconTypes,
|
|
1796
|
+
relayBLEResults: relayBLEResults,
|
|
1510
1797
|
dTimeStates: dTimeStates,
|
|
1511
1798
|
dWorkingStates: dWorkingStates,
|
|
1512
1799
|
gnssTriggerTypes: gnssTriggerTypes,
|
|
@@ -1520,12 +1807,12 @@ module.exports = {
|
|
|
1520
1807
|
includeGnnsAccuracy: includeGnnsAccuracy,
|
|
1521
1808
|
getAccelerationMagnitude: getAccelerationMagnitude,
|
|
1522
1809
|
getTempInCelciousDegrees: getTempInCelciousDegrees,
|
|
1523
|
-
getBtTempHumData: getBtTempHumData,
|
|
1524
1810
|
getFuelConsumption: getFuelConsumption,
|
|
1525
1811
|
getHoursForHourmeter: getHoursForHourmeter,
|
|
1526
1812
|
getSignalStrength: getSignalStrength,
|
|
1527
1813
|
getSignalPercentage: getSignalPercentage,
|
|
1528
1814
|
getCanData: getCanData,
|
|
1815
|
+
getBleData: getBleData,
|
|
1529
1816
|
getAlarm: getAlarm,
|
|
1530
1817
|
bin2dec: bin2dec,
|
|
1531
1818
|
bin2hex: bin2hex,
|