jooby-codec 1.0.1
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/dist/BinaryBuffer.d.ts +44 -0
- package/dist/BinaryBuffer.js +128 -0
- package/dist/BinaryBuffer.js.map +1 -0
- package/dist/Command.d.ts +42 -0
- package/dist/Command.js +80 -0
- package/dist/Command.js.map +1 -0
- package/dist/CommandBinaryBuffer.d.ts +45 -0
- package/dist/CommandBinaryBuffer.js +135 -0
- package/dist/CommandBinaryBuffer.js.map +1 -0
- package/dist/commands/downlink/CorrectTime2000.d.ts +49 -0
- package/dist/commands/downlink/CorrectTime2000.js +61 -0
- package/dist/commands/downlink/CorrectTime2000.js.map +1 -0
- package/dist/commands/downlink/SetTime2000.d.ts +45 -0
- package/dist/commands/downlink/SetTime2000.js +60 -0
- package/dist/commands/downlink/SetTime2000.js.map +1 -0
- package/dist/commands/downlink/index.d.ts +7 -0
- package/dist/commands/downlink/index.js +8 -0
- package/dist/commands/downlink/index.js.map +1 -0
- package/dist/commands/index.d.ts +7 -0
- package/dist/commands/index.js +8 -0
- package/dist/commands/index.js.map +1 -0
- package/dist/commands/uplink/CorrectTime2000.d.ts +37 -0
- package/dist/commands/uplink/CorrectTime2000.js +53 -0
- package/dist/commands/uplink/CorrectTime2000.js.map +1 -0
- package/dist/commands/uplink/DataDayMul.d.ts +20 -0
- package/dist/commands/uplink/DataDayMul.js +41 -0
- package/dist/commands/uplink/DataDayMul.js.map +1 -0
- package/dist/commands/uplink/DataHourMul.d.ts +11 -0
- package/dist/commands/uplink/DataHourMul.js +77 -0
- package/dist/commands/uplink/DataHourMul.js.map +1 -0
- package/dist/commands/uplink/ExAbsDayMul.d.ts +11 -0
- package/dist/commands/uplink/ExAbsDayMul.js +60 -0
- package/dist/commands/uplink/ExAbsDayMul.js.map +1 -0
- package/dist/commands/uplink/ExAbsHourMul.d.ts +11 -0
- package/dist/commands/uplink/ExAbsHourMul.js +92 -0
- package/dist/commands/uplink/ExAbsHourMul.js.map +1 -0
- package/dist/commands/uplink/GetCurrentMul.d.ts +24 -0
- package/dist/commands/uplink/GetCurrentMul.js +35 -0
- package/dist/commands/uplink/GetCurrentMul.js.map +1 -0
- package/dist/commands/uplink/NewEvent.d.ts +18 -0
- package/dist/commands/uplink/NewEvent.js +101 -0
- package/dist/commands/uplink/NewEvent.js.map +1 -0
- package/dist/commands/uplink/SetTime2000.d.ts +37 -0
- package/dist/commands/uplink/SetTime2000.js +53 -0
- package/dist/commands/uplink/SetTime2000.js.map +1 -0
- package/dist/commands/uplink/Time2000.d.ts +41 -0
- package/dist/commands/uplink/Time2000.js +56 -0
- package/dist/commands/uplink/Time2000.js.map +1 -0
- package/dist/commands/uplink/index.d.ts +13 -0
- package/dist/commands/uplink/index.js +14 -0
- package/dist/commands/uplink/index.js.map +1 -0
- package/dist/constants/events.d.ts +16 -0
- package/dist/constants/events.js +17 -0
- package/dist/constants/events.js.map +1 -0
- package/dist/constants/general.d.ts +1 -0
- package/dist/constants/general.js +2 -0
- package/dist/constants/general.js.map +1 -0
- package/dist/constants/index.d.ts +1 -0
- package/dist/constants/index.js +2 -0
- package/dist/constants/index.js.map +1 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.js +5 -0
- package/dist/index.js.map +1 -0
- package/dist/utils/getBitArrayFromNumber.d.ts +14 -0
- package/dist/utils/getBitArrayFromNumber.js +15 -0
- package/dist/utils/getBitArrayFromNumber.js.map +1 -0
- package/dist/utils/getBytesFromHex.d.ts +11 -0
- package/dist/utils/getBytesFromHex.js +23 -0
- package/dist/utils/getBytesFromHex.js.map +1 -0
- package/dist/utils/getHexFromBytes.d.ts +27 -0
- package/dist/utils/getHexFromBytes.js +22 -0
- package/dist/utils/getHexFromBytes.js.map +1 -0
- package/dist/utils/getIntFromBitString.d.ts +6 -0
- package/dist/utils/getIntFromBitString.js +6 -0
- package/dist/utils/getIntFromBitString.js.map +1 -0
- package/dist/utils/header.d.ts +13 -0
- package/dist/utils/header.js +62 -0
- package/dist/utils/header.js.map +1 -0
- package/dist/utils/index.d.ts +2 -0
- package/dist/utils/index.js +3 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/message.d.ts +27 -0
- package/dist/utils/message.js +101 -0
- package/dist/utils/message.js.map +1 -0
- package/dist/utils/roundNumber.d.ts +2 -0
- package/dist/utils/roundNumber.js +5 -0
- package/dist/utils/roundNumber.js.map +1 -0
- package/dist/utils/time.d.ts +14 -0
- package/dist/utils/time.js +17 -0
- package/dist/utils/time.js.map +1 -0
- package/package.json +78 -0
- package/readme.md +145 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"header.js","sourceRoot":"","sources":["../../src/utils/header.ts"],"names":[],"mappings":"AAAA,OAAO,eAAe,MAAM,sBAAsB,CAAC;AACnD,OAAO,eAAoC,MAAM,sBAAsB,CAAC;AAGxE,MAAM,gBAAgB,GAAG,IAAI,CAAC;AAC9B,MAAM,gBAAgB,GAAG,IAAI,CAAC;AAG9B,MAAM,CAAC,MAAM,SAAS,GAAG,CAAE,IAAgB,EAAG,EAAE;IAC5C,IAAK,IAAI,CAAC,MAAM,KAAK,CAAC,EAAG;QACrB,MAAM,IAAI,KAAK,CAAC,qBAAqB,CAAC,CAAC;KAC1C;IAED,MAAM,MAAM,GAAG;QACX,SAAS,EAAE,IAAI,CAAC,CAAC,CAAC,GAAG,gBAAgB;QACrC,SAAS,EAAE,IAAI,CAAC,CAAC,CAAC,GAAG,gBAAgB;KACxC,CAAC;IAEF,IAAK,MAAM,CAAC,SAAS,KAAK,CAAC,EAAG;QAC1B,eAAe;QACf,OAAO;YACH,UAAU,EAAE,CAAC;YACb,SAAS,EAAE,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,MAAM,CAAC,SAAS,CAAC;YACxC,WAAW,EAAE,MAAM,CAAC,SAAS;SAChC,CAAC;KACL;IAED,IAAK,MAAM,CAAC,SAAS,KAAK,gBAAgB,EAAG;QACzC,gBAAgB;QAChB,IAAK,IAAI,CAAC,MAAM,GAAG,CAAC,EAAG;YACnB,MAAM,IAAI,KAAK,CAAC,qBAAqB,CAAC,CAAC;SAC1C;QACD,OAAO;YACH,UAAU,EAAE,CAAC;YACb,SAAS,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,GAAG,gBAAgB;YAC5C,WAAW,EAAE,IAAI,CAAC,CAAC,CAAC;SACvB,CAAC;KACL;IAED,IAAK,IAAI,CAAC,MAAM,GAAG,CAAC,EAAG;QACnB,MAAM,IAAI,KAAK,CAAC,qBAAqB,CAAC,CAAC;KAC1C;IAED,OAAO;QACH,UAAU,EAAE,CAAC;QACb,SAAS,EAAE,MAAM,CAAC,SAAS;QAC3B,WAAW,EAAE,IAAI,CAAC,CAAC,CAAC;KACvB,CAAC;AACN,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,OAAO,GAAG,CAAE,IAAY,EAAG,EAAE,CAAC,SAAS,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC,CAAC;AAE5E,MAAM,CAAC,MAAM,OAAO,GAAG,CAAE,SAAiB,EAAE,WAAmB,EAAe,EAAE;IAC5E,IAAK,CAAC,SAAS,GAAG,gBAAgB,CAAC,KAAK,CAAC,EAAG;QACxC,IAAK,WAAW,GAAG,gBAAgB,EAAG;YAClC,MAAM,IAAI,KAAK,CAAC,8BAA8B,SAAS,WAAW,WAAW,GAAG,CAAC,CAAC;SACrF;QAED,OAAO,IAAI,UAAU,CAAC,CAAC,SAAS,GAAG,WAAW,CAAC,CAAC,CAAC;KACpD;IAED,IAAK,SAAS,GAAG,gBAAgB,EAAG;QAChC,OAAO,IAAI,UAAU,CAAC;YAClB,gBAAgB;YAChB,CAAC,SAAS,IAAI,CAAC,CAAC;YAChB,WAAW;SACd,CAAC,CAAC;KACN;IAED,OAAO,IAAI,UAAU,CAAC;QAClB,SAAS;QACT,WAAW;KACd,CAAC,CAAC;AACP,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,KAAK,GAAG,CAAE,SAAiB,EAAE,WAAmB,EAAE,UAA6B,EAAE,EAAW,EAAE,CAAC,CACxG,eAAe,CAAC,OAAO,CAAC,SAAS,EAAE,WAAW,CAAC,EAAE,OAAO,CAAC,CAC5D,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/utils/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,OAAO,IAAI,eAAe,EAAC,MAAM,sBAAsB,CAAC;AAChE,OAAO,EAAC,OAAO,IAAI,eAAe,EAAoB,MAAM,sBAAsB,CAAC"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import Command from '../Command.js';
|
|
2
|
+
import { IHexFormatOptions } from './getHexFromBytes.js';
|
|
3
|
+
interface IMessageCommand {
|
|
4
|
+
/** command source binary data */
|
|
5
|
+
data: {
|
|
6
|
+
header: Uint8Array;
|
|
7
|
+
body: Uint8Array;
|
|
8
|
+
};
|
|
9
|
+
/** specific command instance */
|
|
10
|
+
command: Command;
|
|
11
|
+
}
|
|
12
|
+
interface IMessage {
|
|
13
|
+
commands: Array<IMessageCommand>;
|
|
14
|
+
lrc: {
|
|
15
|
+
expected: number;
|
|
16
|
+
actual: number;
|
|
17
|
+
};
|
|
18
|
+
isValid: boolean;
|
|
19
|
+
}
|
|
20
|
+
export declare const TYPE_AUTO = 0;
|
|
21
|
+
export declare const TYPE_DOWNLINK = 1;
|
|
22
|
+
export declare const TYPE_UPLINK = 2;
|
|
23
|
+
export declare const fromBytes: (data: Uint8Array, direction?: number) => IMessage;
|
|
24
|
+
export declare const fromHex: (data: string, direction?: number) => IMessage;
|
|
25
|
+
export declare const toBytes: (commands: Array<Command>) => Uint8Array;
|
|
26
|
+
export declare const toHex: (commands: Array<Command>, options?: IHexFormatOptions) => string;
|
|
27
|
+
export {};
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
import * as downlinkCommands from '../commands/downlink/index.js';
|
|
2
|
+
import * as uplinkCommands from '../commands/uplink/index.js';
|
|
3
|
+
import * as header from './header.js';
|
|
4
|
+
import getBytesFromHex from './getBytesFromHex.js';
|
|
5
|
+
import getHexFromBytes from './getHexFromBytes.js';
|
|
6
|
+
export const TYPE_AUTO = 0;
|
|
7
|
+
export const TYPE_DOWNLINK = 1;
|
|
8
|
+
export const TYPE_UPLINK = 2;
|
|
9
|
+
const HEADER_MAX_SIZE = 3;
|
|
10
|
+
// convert export namespace to dictionary {commandId: commandConstructor}
|
|
11
|
+
const downlinkCommandsById = Object.fromEntries(Object.values(downlinkCommands).map(item => [item.id, item]));
|
|
12
|
+
const uplinkCommandsById = Object.fromEntries(Object.values(uplinkCommands).map(item => [item.id, item]));
|
|
13
|
+
/**
|
|
14
|
+
* Calculate LRC
|
|
15
|
+
*
|
|
16
|
+
* @param data - byte array
|
|
17
|
+
*
|
|
18
|
+
* @return LRC
|
|
19
|
+
*/
|
|
20
|
+
const calculateLrc = (data, initialLrc = 0x55) => {
|
|
21
|
+
let lrc = initialLrc;
|
|
22
|
+
data.forEach(item => {
|
|
23
|
+
lrc ^= item;
|
|
24
|
+
});
|
|
25
|
+
return lrc;
|
|
26
|
+
};
|
|
27
|
+
const getCommand = (id, data, direction = TYPE_AUTO) => {
|
|
28
|
+
// given direction
|
|
29
|
+
if (direction === TYPE_DOWNLINK || direction === TYPE_UPLINK) {
|
|
30
|
+
const commandsById = direction === TYPE_DOWNLINK ? downlinkCommandsById : uplinkCommandsById;
|
|
31
|
+
const command = commandsById[id];
|
|
32
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
33
|
+
if (!command) {
|
|
34
|
+
throw new Error(`Unsupported command with id: ${id}.`);
|
|
35
|
+
}
|
|
36
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-return
|
|
37
|
+
return command.fromBytes(data);
|
|
38
|
+
}
|
|
39
|
+
// auto direction
|
|
40
|
+
// try downlink
|
|
41
|
+
try {
|
|
42
|
+
const command = downlinkCommandsById[id];
|
|
43
|
+
// console.log('command downlink:', command);
|
|
44
|
+
// console.log('downlinkCommandsById:', downlinkCommandsById);
|
|
45
|
+
// console.log('id:', id);
|
|
46
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-return
|
|
47
|
+
return command.fromBytes(data);
|
|
48
|
+
}
|
|
49
|
+
catch {
|
|
50
|
+
// try uplink
|
|
51
|
+
const command = uplinkCommandsById[id];
|
|
52
|
+
//console.log('command uplink:', command);
|
|
53
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-return
|
|
54
|
+
return command.fromBytes(data);
|
|
55
|
+
}
|
|
56
|
+
};
|
|
57
|
+
export const fromBytes = (data, direction = TYPE_AUTO) => {
|
|
58
|
+
const commandsData = data.slice(0, -1);
|
|
59
|
+
const expectedLrc = data.at(-1) ?? 0;
|
|
60
|
+
const actualLrc = calculateLrc(commandsData);
|
|
61
|
+
const commands = [];
|
|
62
|
+
const result = {
|
|
63
|
+
commands,
|
|
64
|
+
lrc: { expected: 0, actual: 0 },
|
|
65
|
+
isValid: false
|
|
66
|
+
};
|
|
67
|
+
let position = 0;
|
|
68
|
+
do {
|
|
69
|
+
const headerInfo = header.fromBytes(commandsData.slice(position, position + HEADER_MAX_SIZE));
|
|
70
|
+
const headerData = commandsData.slice(position, position + headerInfo.headerSize);
|
|
71
|
+
const bodyData = commandsData.slice(position + headerInfo.headerSize, position + headerInfo.headerSize + headerInfo.commandSize);
|
|
72
|
+
commands.push({
|
|
73
|
+
data: { header: headerData, body: bodyData },
|
|
74
|
+
command: getCommand(headerInfo.commandId, bodyData, direction)
|
|
75
|
+
});
|
|
76
|
+
// shift
|
|
77
|
+
position = position + headerInfo.headerSize + headerInfo.commandSize;
|
|
78
|
+
} while (position < commandsData.length);
|
|
79
|
+
result.lrc.actual = actualLrc;
|
|
80
|
+
result.lrc.expected = expectedLrc;
|
|
81
|
+
result.isValid = expectedLrc === actualLrc;
|
|
82
|
+
return result;
|
|
83
|
+
};
|
|
84
|
+
export const fromHex = (data, direction = TYPE_AUTO) => fromBytes(getBytesFromHex(data), direction);
|
|
85
|
+
export const toBytes = (commands) => {
|
|
86
|
+
const arrays = commands.map(command => command.toBytes());
|
|
87
|
+
const totalLength = arrays.reduce((accumulator, item) => (accumulator + item.length), 0);
|
|
88
|
+
// 1 additional byte at the end is for LRC
|
|
89
|
+
const result = new Uint8Array(totalLength + 1);
|
|
90
|
+
let offset = 0;
|
|
91
|
+
// fill result with all chunks
|
|
92
|
+
arrays.forEach(item => {
|
|
93
|
+
result.set(item, offset);
|
|
94
|
+
offset += item.length;
|
|
95
|
+
});
|
|
96
|
+
// set last byte to LRC
|
|
97
|
+
result[result.length - 1] = calculateLrc(result.slice(0, result.length - 1));
|
|
98
|
+
return result;
|
|
99
|
+
};
|
|
100
|
+
export const toHex = (commands, options = {}) => getHexFromBytes(toBytes(commands), options);
|
|
101
|
+
//# sourceMappingURL=message.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"message.js","sourceRoot":"","sources":["../../src/utils/message.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"roundNumber.js","sourceRoot":"","sources":["../../src/utils/roundNumber.ts"],"names":[],"mappings":"AAAA,eAAe,CAAE,KAAa,EAAE,aAAa,GAAG,CAAC,EAAG,EAAE;IAClD,MAAM,MAAM,GAAG,EAAE,IAAI,aAAa,CAAC;IAEnC,OAAO,IAAI,CAAC,KAAK,CAAC,CAAC,KAAK,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC,GAAG,MAAM,CAAC,OAAO,CAAC,CAAC,GAAG,MAAM,CAAC;AACxE,CAAC,CAAC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Get date object from UTC seconds since 2000 year.
|
|
3
|
+
*
|
|
4
|
+
* @param time - seconds since 2000 year
|
|
5
|
+
* @returns Date object instance
|
|
6
|
+
*/
|
|
7
|
+
export declare const getDateFromSeconds: (time: number) => Date;
|
|
8
|
+
/**
|
|
9
|
+
* Get UTC seconds since 2000 year from Date object.
|
|
10
|
+
*
|
|
11
|
+
* @param date - Date object
|
|
12
|
+
* @returns seconds since 2000 year
|
|
13
|
+
*/
|
|
14
|
+
export declare const getSecondsFromDate: (date: Date) => number;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
const INITIAL_YEAR_TIMESTAMP = 946684800000;
|
|
2
|
+
const MILLISECONDS_IN_SECONDS = 1000;
|
|
3
|
+
/**
|
|
4
|
+
* Get date object from UTC seconds since 2000 year.
|
|
5
|
+
*
|
|
6
|
+
* @param time - seconds since 2000 year
|
|
7
|
+
* @returns Date object instance
|
|
8
|
+
*/
|
|
9
|
+
export const getDateFromSeconds = (time) => new Date(INITIAL_YEAR_TIMESTAMP + (time * MILLISECONDS_IN_SECONDS));
|
|
10
|
+
/**
|
|
11
|
+
* Get UTC seconds since 2000 year from Date object.
|
|
12
|
+
*
|
|
13
|
+
* @param date - Date object
|
|
14
|
+
* @returns seconds since 2000 year
|
|
15
|
+
*/
|
|
16
|
+
export const getSecondsFromDate = (date) => (date.getTime() - INITIAL_YEAR_TIMESTAMP) / MILLISECONDS_IN_SECONDS;
|
|
17
|
+
//# sourceMappingURL=time.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"time.js","sourceRoot":"","sources":["../../src/utils/time.ts"],"names":[],"mappings":"AAAA,MAAM,sBAAsB,GAAG,YAAY,CAAC;AAC5C,MAAM,uBAAuB,GAAG,IAAI,CAAC;AAGrC;;;;;GAKG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,CAAE,IAAY,EAAS,EAAE,CAAC,IAAI,IAAI,CAAC,sBAAsB,GAAG,CAAC,IAAI,GAAG,uBAAuB,CAAC,CAAC,CAAC;AAEhI;;;;;GAKG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,CAAE,IAAU,EAAW,EAAE,CAAC,CAAC,IAAI,CAAC,OAAO,EAAE,GAAG,sBAAsB,CAAC,GAAG,uBAAuB,CAAC"}
|
package/package.json
ADDED
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "jooby-codec",
|
|
3
|
+
"version": "1.0.1",
|
|
4
|
+
"description": "Jooby message encoders/decoders",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "./dist/index.js",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": "./dist/index.js",
|
|
9
|
+
"./ts": "./src/index.js",
|
|
10
|
+
"./commands": "./dist/commands/index.js",
|
|
11
|
+
"./commands/downlink": "./dist/commands/downlink/index.js",
|
|
12
|
+
"./commands/downlink/*": "./dist/commands/downlink/*.js",
|
|
13
|
+
"./commands/uplink": "./dist/commands/uplink/index.js",
|
|
14
|
+
"./commands/uplink/*": "./dist/commands/uplink/*.js",
|
|
15
|
+
"./utils/*": "./dist/utils/*.js"
|
|
16
|
+
},
|
|
17
|
+
"types": "./dist/index.d.ts",
|
|
18
|
+
"typesVersions": {
|
|
19
|
+
"*": {
|
|
20
|
+
"*": [
|
|
21
|
+
"./dist/index.d.ts",
|
|
22
|
+
"./dist/utils/*.d.ts",
|
|
23
|
+
"./dist/*/index.d.ts"
|
|
24
|
+
],
|
|
25
|
+
"./utils/*": [
|
|
26
|
+
"./dist/utils/*.d.ts"
|
|
27
|
+
]
|
|
28
|
+
}
|
|
29
|
+
},
|
|
30
|
+
"files": [
|
|
31
|
+
"/dist"
|
|
32
|
+
],
|
|
33
|
+
"engines": {
|
|
34
|
+
"npm": ">=9.0.0",
|
|
35
|
+
"node": ">=18.0.0"
|
|
36
|
+
},
|
|
37
|
+
"scripts": {
|
|
38
|
+
"start": "node ./dist/index.js",
|
|
39
|
+
"dev": "nodemon",
|
|
40
|
+
"build:js": "tsc --extendedDiagnostics",
|
|
41
|
+
"build:js:clean": "rm -rf ./dist/ && tsc --incremental false --extendedDiagnostics",
|
|
42
|
+
"build:js:watch": "tsc --watch",
|
|
43
|
+
"build:docs": "typedoc",
|
|
44
|
+
"build:docs:watch": "typedoc --watch --preserveWatchOutput",
|
|
45
|
+
"build": "npm run build:js & npm run build:docs",
|
|
46
|
+
"lint:tsc": "tsc --project ./tsconfig.eslint.json --noEmit",
|
|
47
|
+
"lint:eslint": "eslint ./src ./tests --ext .ts",
|
|
48
|
+
"lint": "npm run lint:tsc && npm run lint:eslint -- --max-warnings=0",
|
|
49
|
+
"lint-cached": "npm run lint:tsc && npm run lint:eslint -- --cache --max-warnings=0",
|
|
50
|
+
"lint:fix": "npm run lint:eslint -- --fix --max-warnings=0",
|
|
51
|
+
"test": "npm run lint && jest",
|
|
52
|
+
"test:watch": "jest --watch",
|
|
53
|
+
"preinstall": "git config core.hooksPath .githooks",
|
|
54
|
+
"publish": "clean-publish"
|
|
55
|
+
},
|
|
56
|
+
"devDependencies": {
|
|
57
|
+
"@types/jest": "^29.5.0",
|
|
58
|
+
"@typescript-eslint/eslint-plugin": "^5.57.0",
|
|
59
|
+
"@typescript-eslint/parser": "^5.57.0",
|
|
60
|
+
"clean-publish": "^4.1.1",
|
|
61
|
+
"eslint": "^8.37.0",
|
|
62
|
+
"eslint-config-airbnb-base": "^15.0.0",
|
|
63
|
+
"eslint-config-airbnb-typescript": "^17.0.0",
|
|
64
|
+
"eslint-import-resolver-typescript": "^3.5.4",
|
|
65
|
+
"eslint-plugin-import": "^2.27.5",
|
|
66
|
+
"eslint-plugin-tsdoc": "^0.2.17",
|
|
67
|
+
"jest": "^29.5.0",
|
|
68
|
+
"nodemon": "^2.0.22",
|
|
69
|
+
"ts-jest": "^29.0.5",
|
|
70
|
+
"ts-node": "^10.9.1",
|
|
71
|
+
"typedoc": "^0.23.28",
|
|
72
|
+
"typedoc-plugin-missing-exports": "^1.0.0",
|
|
73
|
+
"typedoc-theme-hierarchy": "^3.1.0",
|
|
74
|
+
"typedoc-theme-yaf": "^0.0.4",
|
|
75
|
+
"typescript": "^5.0.3"
|
|
76
|
+
},
|
|
77
|
+
"license": "MIT"
|
|
78
|
+
}
|
package/readme.md
ADDED
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
Jooby message encoders/decoders
|
|
2
|
+
===============================
|
|
3
|
+
|
|
4
|
+
[](https://github.com/jooby-dev/jooby-codec/actions)
|
|
5
|
+
[](https://www.npmjs.com/package/jooby-codec)
|
|
6
|
+
[](https://jooby-dev.github.io/jooby-codec)
|
|
7
|
+
|
|
8
|
+
This library contains message encoders and decoders for [Jooby](https://jooby.eu) LoRaWAN devices.
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
## Usage
|
|
12
|
+
|
|
13
|
+
Install required dependencies:
|
|
14
|
+
|
|
15
|
+
```sh
|
|
16
|
+
npm install jooby-codec
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
Add to the project:
|
|
20
|
+
|
|
21
|
+
```js
|
|
22
|
+
import {commands, message} from 'jooby-codec';
|
|
23
|
+
|
|
24
|
+
// output all available commands tree
|
|
25
|
+
console.log(commands);
|
|
26
|
+
// all uplink commands
|
|
27
|
+
console.log(commands.uplink);
|
|
28
|
+
// one particular command
|
|
29
|
+
console.log(commands.uplink.getCurrentMul.default);
|
|
30
|
+
|
|
31
|
+
// output main namespace for work with messages
|
|
32
|
+
console.log(message);
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
But it's better to add only necessary commands to the project:
|
|
36
|
+
|
|
37
|
+
```js
|
|
38
|
+
// to get only downlink commands
|
|
39
|
+
import {downlink} from 'jooby-codec/commands';
|
|
40
|
+
// or slightly more efficient
|
|
41
|
+
import * as downlink from 'jooby-codec/commands/downlink';
|
|
42
|
+
|
|
43
|
+
// to get one particular command
|
|
44
|
+
import SetTime2000 from 'jooby-codec/commands/downlink/SetTime2000';
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
The last approach is preferred as it is more efficient and will init only a necessary commands.
|
|
48
|
+
|
|
49
|
+
It's possible to parse messages either from raw [Uint8Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Uint8Array) or HEX string:
|
|
50
|
+
|
|
51
|
+
Parse downlink message:
|
|
52
|
+
|
|
53
|
+
```js
|
|
54
|
+
// from byte array
|
|
55
|
+
const messageData = message.fromBytes(
|
|
56
|
+
new Uint8Array([
|
|
57
|
+
0x02, 0x05, 0x4e, 0x00, 0x01, 0xe2, 0x40,
|
|
58
|
+
0x02, 0x05, 0x4e, 0x00, 0x01, 0xe2, 0x40,
|
|
59
|
+
0x55
|
|
60
|
+
]),
|
|
61
|
+
message.TYPE_DOWNLINK
|
|
62
|
+
);
|
|
63
|
+
// or from hex string
|
|
64
|
+
const messageData = message.fromHex(
|
|
65
|
+
'02 05 4e 00 01 e2 40 02 05 4e 00 01 e2 40 55',
|
|
66
|
+
message.TYPE_DOWNLINK
|
|
67
|
+
);
|
|
68
|
+
|
|
69
|
+
// decoded data with commands and checksum
|
|
70
|
+
console.log(messageData);
|
|
71
|
+
/*{
|
|
72
|
+
commands: [
|
|
73
|
+
{ data: [Object], command: [SetTime2000] },
|
|
74
|
+
{ data: [Object], command: [SetTime2000] }
|
|
75
|
+
],
|
|
76
|
+
lrc: { expected: 85, actual: 85 },
|
|
77
|
+
isValid: true
|
|
78
|
+
}*/
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
Parse uplink message:
|
|
82
|
+
|
|
83
|
+
```js
|
|
84
|
+
const messageData = message.fromHex(
|
|
85
|
+
'02 01 01 18 06 0f 83 01 08 0a 0c 16 08 2f 97 0f 83 01 08 0a 0c ef',
|
|
86
|
+
message.TYPE_UPLINK
|
|
87
|
+
);
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
It's possible to parse message with autodetect direction:
|
|
91
|
+
|
|
92
|
+
```js
|
|
93
|
+
const messageData = message.fromHex(
|
|
94
|
+
'02 01 01 18 06 0f 83 01 08 0a 0c 16 08 2f 97 0f 83 01 08 0a 0c ef',
|
|
95
|
+
message.TYPE_AUTO
|
|
96
|
+
);
|
|
97
|
+
// or even shorter as message.TYPE_AUTO is default behavior
|
|
98
|
+
const messageData = message.fromHex(
|
|
99
|
+
'02 01 01 18 06 0f 83 01 08 0a 0c 16 08 2f 97 0f 83 01 08 0a 0c ef'
|
|
100
|
+
);
|
|
101
|
+
```
|
|
102
|
+
It's best to avoid using message.TYPE_AUTO due to performance penalty.
|
|
103
|
+
|
|
104
|
+
Prepare command and get encoded data:
|
|
105
|
+
|
|
106
|
+
```js
|
|
107
|
+
import SetTime2000 from 'jooby-codec/commands/downlink/SetTime2000';
|
|
108
|
+
|
|
109
|
+
const command = new SetTime2000({sequenceNumber: 5, time: 9462957});
|
|
110
|
+
|
|
111
|
+
// output command binary in hex representation
|
|
112
|
+
// 02 05 05 00 90 64 ad
|
|
113
|
+
console.log(command.toHex());
|
|
114
|
+
// [2, 5, 5, 0, 144, 100, 173]
|
|
115
|
+
console.log(command.toBytes());
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
Combine a message from commands:
|
|
119
|
+
|
|
120
|
+
```js
|
|
121
|
+
const messageBytes = message.toBytes([
|
|
122
|
+
new SetTime2000({sequenceNumber: 78, time: 123456}),
|
|
123
|
+
new GetCurrent()
|
|
124
|
+
]);
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
or to get in a hex format:
|
|
128
|
+
|
|
129
|
+
```js
|
|
130
|
+
const commandInstancesArray = [
|
|
131
|
+
new SetTime2000({status: 1}),
|
|
132
|
+
new DataDayMul({
|
|
133
|
+
channels: [
|
|
134
|
+
{value: 131, index: 0},
|
|
135
|
+
{value: 8, index: 1},
|
|
136
|
+
{value: 10, index: 2},
|
|
137
|
+
{value: 12, index: 3}
|
|
138
|
+
],
|
|
139
|
+
time: 75660480
|
|
140
|
+
})
|
|
141
|
+
];
|
|
142
|
+
|
|
143
|
+
const messageBytes = message.toHex(commandInstancesArray, {prefix: '0x'});
|
|
144
|
+
// 0x02 0x05 0x05 0x00 0x90 ...
|
|
145
|
+
```
|