@canboat/canboatjs 2.6.0 → 2.8.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.
- package/bin/analyzerjs +4 -1
- package/lib/candevice.js +34 -2
- package/lib/fromPgn.js +5 -1
- package/lib/stringMsg.js +30 -8
- package/lib/toPgn.js +0 -13
- package/package.json +2 -2
package/bin/analyzerjs
CHANGED
|
@@ -2,7 +2,8 @@
|
|
|
2
2
|
|
|
3
3
|
const argv = require('minimist')(process.argv.slice(2), {
|
|
4
4
|
alias: { h: 'help' },
|
|
5
|
-
boolean: ['n']
|
|
5
|
+
boolean: ['n'],
|
|
6
|
+
boolean: ['r']
|
|
6
7
|
})
|
|
7
8
|
|
|
8
9
|
if ( argv['help'] ) {
|
|
@@ -11,6 +12,7 @@ if ( argv['help'] ) {
|
|
|
11
12
|
Options:
|
|
12
13
|
-c don't check for invalid values
|
|
13
14
|
-n output null values
|
|
15
|
+
-r parse $MXPGN as little endian
|
|
14
16
|
-h, --help output usage information`)
|
|
15
17
|
process.exit(1)
|
|
16
18
|
}
|
|
@@ -18,6 +20,7 @@ Options:
|
|
|
18
20
|
const Parser = require('../index').FromPgn
|
|
19
21
|
var parser = new Parser( {
|
|
20
22
|
returnNulls: argv['n'] === true,
|
|
23
|
+
littleEndianMXPGN: argv['r'] === true,
|
|
21
24
|
checkForInvalidFields: argv['c'] !== true
|
|
22
25
|
})
|
|
23
26
|
|
package/lib/candevice.js
CHANGED
|
@@ -20,6 +20,13 @@ const _ = require('lodash')
|
|
|
20
20
|
const Uint64LE = require('int64-buffer').Uint64LE
|
|
21
21
|
const { defaultTransmitPGNs, getIndustryCode, getManufacturerCode, getDeviceClassCode } = require('./codes')
|
|
22
22
|
const { toPgn } = require('./toPgn')
|
|
23
|
+
let packageJson
|
|
24
|
+
|
|
25
|
+
try
|
|
26
|
+
{
|
|
27
|
+
packageJson = require('../' + 'package.json')
|
|
28
|
+
} catch (ex) {
|
|
29
|
+
}
|
|
23
30
|
|
|
24
31
|
const deviceTransmitPGNs = [ 60928, 59904, 126996, 126464 ]
|
|
25
32
|
|
|
@@ -31,10 +38,12 @@ class CanDevice extends EventEmitter {
|
|
|
31
38
|
this.addressClaim = options.addressClaim
|
|
32
39
|
this.addressClaim.pgn = 60928
|
|
33
40
|
this.addressClaim.dst = 255
|
|
41
|
+
this.addressClaim.prio = 6
|
|
34
42
|
} else {
|
|
35
43
|
this.addressClaim = {
|
|
36
44
|
pgn: 60928,
|
|
37
45
|
dst: 255,
|
|
46
|
+
prio:6,
|
|
38
47
|
"Unique Number": 1263,
|
|
39
48
|
"Manufacturer Code": 999,
|
|
40
49
|
"Device Function": 130, // PC gateway
|
|
@@ -49,6 +58,8 @@ class CanDevice extends EventEmitter {
|
|
|
49
58
|
this.addressClaim["Unique Number"] = options.uniqueNumber || Math.floor(Math.random() * Math.floor(2097151))
|
|
50
59
|
}
|
|
51
60
|
|
|
61
|
+
let version = packageJson ? packageJson.version : "1.0"
|
|
62
|
+
|
|
52
63
|
if ( options.productInfo ) {
|
|
53
64
|
this.productInfo = options.productInfo
|
|
54
65
|
this.productInfo.pgn = 126996
|
|
@@ -60,14 +71,25 @@ class CanDevice extends EventEmitter {
|
|
|
60
71
|
"NMEA 2000 Version": 1300,
|
|
61
72
|
"Product Code": 667, // Just made up..
|
|
62
73
|
"Model ID": "Signal K",
|
|
63
|
-
"
|
|
64
|
-
"Model Version": "canbusjs",
|
|
74
|
+
"Model Version": "canboatjs",
|
|
65
75
|
"Model Serial Code": options.uniqueNumber ? options.uniqueNumber.toString() : "000001",
|
|
66
76
|
"Certification Level": 0,
|
|
67
77
|
"Load Equivalency": 1
|
|
68
78
|
}
|
|
69
79
|
}
|
|
70
80
|
|
|
81
|
+
this.productInfo["Software Version Code"] = version
|
|
82
|
+
|
|
83
|
+
if ( options.serverVersion && options.serverUrl ) {
|
|
84
|
+
this.configurationInfo = {
|
|
85
|
+
pgn: 126998,
|
|
86
|
+
dst: 255,
|
|
87
|
+
"Installation Description #1": options.serverUrl,
|
|
88
|
+
"Installation Description #2": options.serverDescription,
|
|
89
|
+
"Manufacturer Information": options.serverVersion
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
|
|
71
93
|
this.canbus = canbus
|
|
72
94
|
this.options = _.isUndefined(options) ? {} : options
|
|
73
95
|
|
|
@@ -142,6 +164,9 @@ function handleISORequest(device, n2kMsg) {
|
|
|
142
164
|
case 126996: // Product Information request
|
|
143
165
|
sendProductInformation(device)
|
|
144
166
|
break;
|
|
167
|
+
case 126998: // Config Information request
|
|
168
|
+
sendConfigInformation(device)
|
|
169
|
+
break;
|
|
145
170
|
case 60928: // ISO address claim request
|
|
146
171
|
sendPGN(device, device.addressClaim)
|
|
147
172
|
break;
|
|
@@ -290,6 +315,13 @@ function sendProductInformation(device) {
|
|
|
290
315
|
sendPGN(device, device.productInfo)
|
|
291
316
|
}
|
|
292
317
|
|
|
318
|
+
function sendConfigInformation(device) {
|
|
319
|
+
if ( device.configurationInfo ) {
|
|
320
|
+
debug("Sending config info..")
|
|
321
|
+
sendPGN(device, device.configurationInfo)
|
|
322
|
+
}
|
|
323
|
+
}
|
|
324
|
+
|
|
293
325
|
function sendNAKAcknowledgement(device, src, requestedPGN) {
|
|
294
326
|
const acknowledgement = {
|
|
295
327
|
pgn: 59392,
|
package/lib/fromPgn.js
CHANGED
|
@@ -233,6 +233,10 @@ class Parser extends EventEmitter {
|
|
|
233
233
|
} else {
|
|
234
234
|
const ts = _.get(pgn, 'timestamp', new Date())
|
|
235
235
|
pgn.timestamp = _.isDate(ts) ? ts.toISOString() : ts
|
|
236
|
+
if ( !_.isUndefined(value) && (value != null ||
|
|
237
|
+
this.options.returnNulls) ) {
|
|
238
|
+
pgn.fields[field.Name] = value
|
|
239
|
+
}
|
|
236
240
|
this.emit('pgn', pgn)
|
|
237
241
|
cb && cb(undefined, pgn)
|
|
238
242
|
return pgn
|
|
@@ -454,7 +458,7 @@ class Parser extends EventEmitter {
|
|
|
454
458
|
|
|
455
459
|
parseString (pgn_data, cb) {
|
|
456
460
|
try {
|
|
457
|
-
const { coalesced, data, error, len, ...pgn } = parseN2kString(pgn_data)
|
|
461
|
+
const { coalesced, data, error, len, ...pgn } = parseN2kString(pgn_data, this.options)
|
|
458
462
|
if (error) {
|
|
459
463
|
cb && cb(error)
|
|
460
464
|
this.emit('error', pgn, error)
|
package/lib/stringMsg.js
CHANGED
|
@@ -19,13 +19,17 @@ const {
|
|
|
19
19
|
* @param {Object} [rest={}] Anything else to be added like len, timestamp, direction.
|
|
20
20
|
* @return {Object} All canId fields with format and data props added.
|
|
21
21
|
*/
|
|
22
|
-
function buildMsg(
|
|
23
|
-
|
|
24
|
-
...canIdInfo,
|
|
22
|
+
function buildMsg(_canIdInfo, format, data, rest = {}) {
|
|
23
|
+
const canIdInfo = Object.assign({}, _canIdInfo, {
|
|
25
24
|
format,
|
|
26
|
-
data
|
|
27
|
-
|
|
25
|
+
data
|
|
26
|
+
})
|
|
27
|
+
for (const property in rest) {
|
|
28
|
+
if (canIdInfo[property] === undefined) {
|
|
29
|
+
canIdInfo[property] = rest[property]
|
|
30
|
+
}
|
|
28
31
|
}
|
|
32
|
+
return canIdInfo
|
|
29
33
|
}
|
|
30
34
|
function buildErrMsg(msg, input) {
|
|
31
35
|
if (input && isString(input)) return `${msg} - ${input}`
|
|
@@ -41,7 +45,8 @@ function toPaddedHexString(num, len) {
|
|
|
41
45
|
}
|
|
42
46
|
|
|
43
47
|
// 2016-02-28T19:57:02.364Z,2,127250,7,255,8,ff,10,3b,ff,7f,ce,f5,fc
|
|
44
|
-
exports.isActisense = input => input.charAt(10) === 'T' && input.charAt(23) === 'Z'
|
|
48
|
+
exports.isActisense = input => (input.charAt(10) === 'T' && input.charAt(23) === 'Z') || (input.charAt(10) === '-' && input.charAt(23) === ',')
|
|
49
|
+
|
|
45
50
|
exports.parseActisense = (input) => {
|
|
46
51
|
const [ timestamp, prio, pgn, src, dst, len, ...data ] = input.split(',')
|
|
47
52
|
return buildMsg(
|
|
@@ -151,12 +156,22 @@ exports.encodePCDIN = ({ prefix = '$PCDIN', pgn, data, dst = 255}) => {
|
|
|
151
156
|
return sentence + compute0183Checksum(sentence)
|
|
152
157
|
}
|
|
153
158
|
|
|
159
|
+
const changeEndianness = (string) => {
|
|
160
|
+
const result = [];
|
|
161
|
+
let len = string.length - 2;
|
|
162
|
+
while (len >= 0) {
|
|
163
|
+
result.push(string.substr(len, 2));
|
|
164
|
+
len -= 2;
|
|
165
|
+
}
|
|
166
|
+
return result.join('');
|
|
167
|
+
}
|
|
168
|
+
|
|
154
169
|
// $MXPGN,01F801,2801,C1308AC40C5DE343*19
|
|
155
170
|
exports.isMXPGN = (msg) => {
|
|
156
171
|
const sentence = get0183Sentence(msg)
|
|
157
172
|
return sentence.startsWith('$MXPGN,')
|
|
158
173
|
}
|
|
159
|
-
exports.parseMXPGN = (input) => {
|
|
174
|
+
exports.parseMXPGN = (input, options) => {
|
|
160
175
|
const sentence = get0183Sentence(input)
|
|
161
176
|
const [ prefix, pgn, attr_word, data ] = sentence.split(',')
|
|
162
177
|
|
|
@@ -167,11 +182,18 @@ exports.parseMXPGN = (input) => {
|
|
|
167
182
|
const len = parseInt(send_prio_len.substr(4,4), 2);
|
|
168
183
|
let src, dst;
|
|
169
184
|
send ? dst = addr: src = addr;
|
|
185
|
+
|
|
186
|
+
let reversed
|
|
187
|
+
|
|
188
|
+
if ( options && options.littleEndianMXPGN )
|
|
189
|
+
reversed = changeEndianness(rmChecksum(data))
|
|
190
|
+
else
|
|
191
|
+
reversed = data
|
|
170
192
|
|
|
171
193
|
return buildMsg(
|
|
172
194
|
buildCanId(0, parseInt(pgn, 16), 255, parseInt(src, 16)),
|
|
173
195
|
'MXPGN',
|
|
174
|
-
Buffer.from(
|
|
196
|
+
Buffer.from(reversed, 'hex'),
|
|
175
197
|
{ coalesced: true, prefix },
|
|
176
198
|
)
|
|
177
199
|
}
|
package/lib/toPgn.js
CHANGED
|
@@ -54,19 +54,6 @@ function toPgn(data) {
|
|
|
54
54
|
const pgn_number = data.pgn
|
|
55
55
|
var pgnData = pgnList[0]
|
|
56
56
|
|
|
57
|
-
if ( pgnList.length > 1 && data['Manufacturer Code'] ) {
|
|
58
|
-
pgnData = pgnList.find(pgn => {
|
|
59
|
-
let mc = pgn.Fields.find(field => (field.Name === 'Manufacturer Code'))
|
|
60
|
-
//console.log(`mc ${JSON.stringify(mc)}`)
|
|
61
|
-
return mc && mc.Match && mc.Match == data['Manufacturer Code']
|
|
62
|
-
})
|
|
63
|
-
if ( !pgnData )
|
|
64
|
-
{
|
|
65
|
-
debug("no pgn found: " + data.pgn)
|
|
66
|
-
return undefined
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
|
|
70
57
|
var bs = new BitStream(Buffer.alloc(500))
|
|
71
58
|
|
|
72
59
|
if ( data.fields ) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@canboat/canboatjs",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.8.0",
|
|
4
4
|
"description": "Native javascript version of canboat",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"scripts": {
|
|
@@ -55,7 +55,7 @@
|
|
|
55
55
|
],
|
|
56
56
|
"license": "Apache-2.0",
|
|
57
57
|
"dependencies": {
|
|
58
|
-
"@canboat/pgns": "
|
|
58
|
+
"@canboat/pgns": "5.1.x",
|
|
59
59
|
"bit-buffer": "0.2.3",
|
|
60
60
|
"debug": "^4.3.4",
|
|
61
61
|
"dnssd": "^0.4.1",
|