Skip to content

Commit 6f9ebf8

Browse files
committed
feat(Parser): allow left-padded values
1 parent 22c6952 commit 6f9ebf8

File tree

2 files changed

+45
-15
lines changed

2 files changed

+45
-15
lines changed

Diff for: src/msgAggregatorWorker.test.ts

+20
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,26 @@ describe("Parsing data", () => {
101101
);
102102
});
103103

104+
test("labeled padded", () => {
105+
const messages = [
106+
`0${trailingFieldDelimiter}${recordDelimiter}`,
107+
`label_1: 1${fieldDelimiter}label_2: 20${trailingFieldDelimiter}${recordDelimiter}`,
108+
`label_1: 300${fieldDelimiter}label_2:4000${trailingFieldDelimiter}${recordDelimiter}`,
109+
];
110+
111+
const assertion = {
112+
datasetNames: ["label_1", "label_2"],
113+
parsedLines: [
114+
{ label_1: 1, label_2: 20 },
115+
{ label_1: 300, label_2: 4000 },
116+
],
117+
};
118+
119+
expect(messageAggregator.parseSerialMessages(messages)).toEqual(
120+
assertion
121+
);
122+
});
123+
104124
test("buffering", () => {
105125
// Incomplete record
106126
let messages = [

Diff for: src/msgAggregatorWorker.ts

+25-15
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,9 @@ ctx.addEventListener("message", (event) => {
1818

1919
let buffer = "";
2020
let discardFirstLine = true;
21-
const separator = "\r?\n";
21+
const lineSeparator = "\r?\n";
2222
const delimiter = "[, \t]+"; // Serial Plotter protocol supports Comma, Space & Tab characters as delimiters
23-
var separatorRegex = new RegExp(`(${separator})`, "g");
23+
var lineSeparatorRegex = new RegExp(`(${lineSeparator})`, "g");
2424
var delimiterRegex = new RegExp(delimiter, "g");
2525

2626
export const parseSerialMessages = (
@@ -33,8 +33,8 @@ export const parseSerialMessages = (
3333
// so we need to discard it and start aggregating from the first encountered separator
3434
let joinMessages = messages.join("");
3535
if (discardFirstLine) {
36-
separatorRegex.lastIndex = 0; // Reset lastIndex to ensure match happens from beginning of string
37-
const separatorMatch = separatorRegex.exec(joinMessages);
36+
lineSeparatorRegex.lastIndex = 0; // Reset lastIndex to ensure match happens from beginning of string
37+
const separatorMatch = lineSeparatorRegex.exec(joinMessages);
3838
if (separatorMatch && separatorMatch.index > -1) {
3939
joinMessages = joinMessages.substring(
4040
separatorMatch.index + separatorMatch[0].length
@@ -50,14 +50,16 @@ export const parseSerialMessages = (
5050

5151
//add any leftover from the buffer to the first line
5252
const messagesAndBuffer = ((buffer || "") + joinMessages)
53-
.split(separatorRegex)
53+
.split(lineSeparatorRegex)
5454
.filter((message) => message.length > 0);
5555

5656
// remove the previous buffer
5757
buffer = "";
58-
separatorRegex.lastIndex = 0;
58+
lineSeparatorRegex.lastIndex = 0;
5959
// check if the last message contains the delimiter, if not, it's an incomplete string that needs to be added to the buffer
60-
if (!separatorRegex.test(messagesAndBuffer[messagesAndBuffer.length - 1])) {
60+
if (
61+
!lineSeparatorRegex.test(messagesAndBuffer[messagesAndBuffer.length - 1])
62+
) {
6163
buffer = messagesAndBuffer[messagesAndBuffer.length - 1];
6264
messagesAndBuffer.splice(-1);
6365
}
@@ -66,10 +68,15 @@ export const parseSerialMessages = (
6668
const parsedLines: { [key: string]: number }[] = [];
6769

6870
// for each line, explode variables
69-
separatorRegex.lastIndex = 0;
71+
lineSeparatorRegex.lastIndex = 0;
7072
messagesAndBuffer
71-
.filter((message) => !separatorRegex.test(message))
73+
.filter((message) => !lineSeparatorRegex.test(message))
7274
.forEach((message) => {
75+
// replace all delimiters with a single space for uniform parsing
76+
message = message.replace(delimiterRegex, " ");
77+
// replace multiple spaces with a single space
78+
message = message.replace(/\s+/g, " ");
79+
7380
const parsedLine: { [key: string]: number } = {};
7481

7582
// Part Separator symbols i.e. Space, Tab & Comma are fully supported
@@ -80,12 +87,15 @@ export const parseSerialMessages = (
8087
// if we find a colon, we assume the latter is being used
8188
let tokens: string[] = [];
8289
if (message.indexOf(":") > 0) {
83-
message.split(delimiterRegex).forEach((keyValue: string) => {
84-
let [key, value] = keyValue.split(":");
85-
key = key && key.trim();
86-
value = value && value.trim();
87-
if (key && key.length > 0 && value && value.length > 0) {
88-
tokens.push(...[key, value]);
90+
// Splitting by the separator and handling possible spaces
91+
const keyValuePairs = message.split(":").map((kv) => kv.trim());
92+
let reformedLine = keyValuePairs.join(":").split(delimiterRegex);
93+
94+
reformedLine.forEach((kv) => {
95+
const [key, value] = kv.split(":");
96+
if (key && value) {
97+
tokens.push(key.trim());
98+
tokens.push(value.trim());
8999
}
90100
});
91101
} else {

0 commit comments

Comments
 (0)