Skip to content

Commit 9c5a826

Browse files
MDCurrentnsarrazin
andauthored
Bug Fix: Json Decoder aggessively pulls json (#867)
* wait for newline char b4 decoding json * remove noisy console log * linters --------- Co-authored-by: Nathan Sarrazin <sarrazin.nathan@gmail.com>
1 parent 3abaf81 commit 9c5a826

File tree

1 file changed

+47
-26
lines changed

1 file changed

+47
-26
lines changed

src/lib/server/endpoints/llamacpp/endpointLlamacpp.ts

Lines changed: 47 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -55,10 +55,13 @@ export function endpointLlamacpp(
5555
let stop = false;
5656
let generatedText = "";
5757
let tokenId = 0;
58+
let accumulatedData = ""; // Buffer to accumulate data chunks
59+
5860
while (!stop) {
59-
// read the stream and log the outputs to console
61+
// Read the stream and log the outputs to console
6062
const out = (await reader?.read()) ?? { done: false, value: undefined };
61-
// we read, if it's done we cancel
63+
64+
// If it's done, we cancel
6265
if (out.done) {
6366
reader?.cancel();
6467
return;
@@ -68,31 +71,49 @@ export function endpointLlamacpp(
6871
return;
6972
}
7073

71-
if (out.value.startsWith("data: ")) {
72-
let data = null;
73-
try {
74-
data = JSON.parse(out.value.slice(6));
75-
} catch (e) {
76-
return;
77-
}
78-
if (data.content || data.stop) {
79-
generatedText += data.content;
80-
const output: TextGenerationStreamOutput = {
81-
token: {
82-
id: tokenId++,
83-
text: data.content ?? "",
84-
logprob: 0,
85-
special: false,
86-
},
87-
generated_text: data.stop ? generatedText : null,
88-
details: null,
89-
};
90-
if (data.stop) {
91-
stop = true;
92-
reader?.cancel();
74+
// Accumulate the data chunk
75+
accumulatedData += out.value;
76+
77+
// Process each complete JSON object in the accumulated data
78+
while (accumulatedData.includes("\n")) {
79+
// Assuming each JSON object ends with a newline
80+
const endIndex = accumulatedData.indexOf("\n");
81+
let jsonString = accumulatedData.substring(0, endIndex).trim();
82+
83+
// Remove the processed part from the buffer
84+
accumulatedData = accumulatedData.substring(endIndex + 1);
85+
86+
if (jsonString.startsWith("data: ")) {
87+
jsonString = jsonString.slice(6);
88+
let data = null;
89+
90+
try {
91+
data = JSON.parse(jsonString);
92+
} catch (e) {
93+
console.error("Failed to parse JSON", e);
94+
console.error("Problematic JSON string:", jsonString);
95+
continue; // Skip this iteration and try the next chunk
96+
}
97+
98+
// Handle the parsed data
99+
if (data.content || data.stop) {
100+
generatedText += data.content;
101+
const output: TextGenerationStreamOutput = {
102+
token: {
103+
id: tokenId++,
104+
text: data.content ?? "",
105+
logprob: 0,
106+
special: false,
107+
},
108+
generated_text: data.stop ? generatedText : null,
109+
details: null,
110+
};
111+
if (data.stop) {
112+
stop = true;
113+
reader?.cancel();
114+
}
115+
yield output;
93116
}
94-
yield output;
95-
// take the data.content value and yield it
96117
}
97118
}
98119
}

0 commit comments

Comments
 (0)