SimpleChat: Add MultiPart Response handling, common trimming
Add logic to call into multipart/stream server response handling. Move trimming of garbage at the end into the common handle_response helper. Add new global flag to control between oneshot and multipart/stream mode of fetching response. Allow same to be controlled by user. If in multipart/stream mode, send the stream flag to the server.
This commit is contained in:
parent
aecf0e23fd
commit
08b117b4a7
1 changed files with 40 additions and 19 deletions
|
@ -155,6 +155,7 @@ class SimpleChat {
|
||||||
/**
|
/**
|
||||||
* Add needed fields wrt json object to be sent wrt LLM web services completions endpoint.
|
* Add needed fields wrt json object to be sent wrt LLM web services completions endpoint.
|
||||||
* The needed fields/options are picked from a global object.
|
* The needed fields/options are picked from a global object.
|
||||||
|
* Add optional stream flag, if required.
|
||||||
* Convert the json into string.
|
* Convert the json into string.
|
||||||
* @param {Object} obj
|
* @param {Object} obj
|
||||||
*/
|
*/
|
||||||
|
@ -162,6 +163,9 @@ class SimpleChat {
|
||||||
for(let k in gMe.chatRequestOptions) {
|
for(let k in gMe.chatRequestOptions) {
|
||||||
obj[k] = gMe.chatRequestOptions[k];
|
obj[k] = gMe.chatRequestOptions[k];
|
||||||
}
|
}
|
||||||
|
if (gMe.bStream) {
|
||||||
|
obj["stream"] = true;
|
||||||
|
}
|
||||||
return JSON.stringify(obj);
|
return JSON.stringify(obj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -217,25 +221,17 @@ class SimpleChat {
|
||||||
* @param {string} apiEP
|
* @param {string} apiEP
|
||||||
*/
|
*/
|
||||||
response_extract(respBody, apiEP) {
|
response_extract(respBody, apiEP) {
|
||||||
let theResp = {
|
let assistant = "";
|
||||||
assistant: "",
|
|
||||||
trimmed: "",
|
|
||||||
}
|
|
||||||
if (apiEP == ApiEP.Type.Chat) {
|
if (apiEP == ApiEP.Type.Chat) {
|
||||||
theResp.assistant = respBody["choices"][0]["message"]["content"];
|
assistant = respBody["choices"][0]["message"]["content"];
|
||||||
} else {
|
} else {
|
||||||
try {
|
try {
|
||||||
theResp.assistant = respBody["choices"][0]["text"];
|
assistant = respBody["choices"][0]["text"];
|
||||||
} catch {
|
} catch {
|
||||||
theResp.assistant = respBody["content"];
|
assistant = respBody["content"];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (gMe.bTrimGarbage) {
|
return assistant;
|
||||||
let origMsg = theResp.assistant;
|
|
||||||
theResp.assistant = du.trim_garbage_at_end(theResp.assistant);
|
|
||||||
theResp.trimmed = origMsg.substring(theResp.assistant.length);
|
|
||||||
}
|
|
||||||
return theResp;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -344,7 +340,7 @@ class SimpleChat {
|
||||||
}
|
}
|
||||||
let curJson = JSON.parse(curArray);
|
let curJson = JSON.parse(curArray);
|
||||||
console.debug("DBUG:SC:PART:Json:", curJson);
|
console.debug("DBUG:SC:PART:Json:", curJson);
|
||||||
gotBody += chat.response_extract_stream(curJson, gMe.apiEP);
|
gotBody += this.response_extract_stream(curJson, apiEP);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (done) {
|
if (done) {
|
||||||
|
@ -366,10 +362,28 @@ class SimpleChat {
|
||||||
return this.response_extract(respBody, apiEP);
|
return this.response_extract(respBody, apiEP);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle the response from the server be it in oneshot or multipart/stream mode.
|
||||||
|
* Also take care of the optional garbage trimming.
|
||||||
|
* @param {Response} resp
|
||||||
|
* @param {string} apiEP
|
||||||
|
*/
|
||||||
async handle_response(resp, apiEP) {
|
async handle_response(resp, apiEP) {
|
||||||
if (apiEP == ApiEP.Type.Chat) {
|
let theResp = {
|
||||||
return this.handle_response_oneshot(resp, apiEP);
|
assistant: "",
|
||||||
|
trimmed: "",
|
||||||
}
|
}
|
||||||
|
let origMsg;
|
||||||
|
if (gMe.bStream) {
|
||||||
|
origMsg = await this.handle_response_multipart(resp, apiEP);
|
||||||
|
} else {
|
||||||
|
origMsg = await this.handle_response_oneshot(resp, apiEP);
|
||||||
|
}
|
||||||
|
if (gMe.bTrimGarbage) {
|
||||||
|
theResp.assistant = du.trim_garbage_at_end(origMsg);
|
||||||
|
theResp.trimmed = origMsg.substring(theResp.assistant.length);
|
||||||
|
}
|
||||||
|
return theResp;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -532,8 +546,7 @@ class MultiChatUI {
|
||||||
body: theBody,
|
body: theBody,
|
||||||
});
|
});
|
||||||
|
|
||||||
let respBody = await this.read_json_early(chat, resp);
|
let theResp = await chat.handle_response(resp, apiEP);
|
||||||
let theResp = chat.handle_response(respBody, apiEP);
|
|
||||||
chat.add(Roles.Assistant, theResp.assistant);
|
chat.add(Roles.Assistant, theResp.assistant);
|
||||||
if (chatId == this.curChatId) {
|
if (chatId == this.curChatId) {
|
||||||
chat.show(this.elDivChat);
|
chat.show(this.elDivChat);
|
||||||
|
@ -628,6 +641,7 @@ class Me {
|
||||||
constructor() {
|
constructor() {
|
||||||
this.defaultChatIds = [ "Default", "Other" ];
|
this.defaultChatIds = [ "Default", "Other" ];
|
||||||
this.multiChat = new MultiChatUI();
|
this.multiChat = new MultiChatUI();
|
||||||
|
this.bStream = true;
|
||||||
this.bCompletionFreshChatAlways = true;
|
this.bCompletionFreshChatAlways = true;
|
||||||
this.bCompletionInsertStandardRolePrefix = false;
|
this.bCompletionInsertStandardRolePrefix = false;
|
||||||
this.bTrimGarbage = true;
|
this.bTrimGarbage = true;
|
||||||
|
@ -659,6 +673,8 @@ class Me {
|
||||||
let p = ui.el_create_append_p("Settings (devel-tools-console document[gMe])", elDiv);
|
let p = ui.el_create_append_p("Settings (devel-tools-console document[gMe])", elDiv);
|
||||||
p.className = "role-system";
|
p.className = "role-system";
|
||||||
|
|
||||||
|
ui.el_create_append_p(`bStream:${this.bStream}`, elDiv);
|
||||||
|
|
||||||
ui.el_create_append_p(`bCompletionFreshChatAlways:${this.bCompletionFreshChatAlways}`, elDiv);
|
ui.el_create_append_p(`bCompletionFreshChatAlways:${this.bCompletionFreshChatAlways}`, elDiv);
|
||||||
|
|
||||||
ui.el_create_append_p(`bCompletionInsertStandardRolePrefix:${this.bCompletionInsertStandardRolePrefix}`, elDiv);
|
ui.el_create_append_p(`bCompletionInsertStandardRolePrefix:${this.bCompletionInsertStandardRolePrefix}`, elDiv);
|
||||||
|
@ -679,7 +695,12 @@ class Me {
|
||||||
*/
|
*/
|
||||||
show_settings(elDiv) {
|
show_settings(elDiv) {
|
||||||
|
|
||||||
let bb = ui.el_creatediv_boolbutton("SetCompletionFreshChatAlways", "CompletionFreshChatAlways", {true: "[+] yes fresh", false: "[-] no, with history"}, this.bCompletionFreshChatAlways, (val)=>{
|
let bb = ui.el_creatediv_boolbutton("SetStream", "Stream", {true: "[+] yes stream", false: "[-] do oneshot"}, this.bStream, (val)=>{
|
||||||
|
this.bStream = val;
|
||||||
|
});
|
||||||
|
elDiv.appendChild(bb);
|
||||||
|
|
||||||
|
bb = ui.el_creatediv_boolbutton("SetCompletionFreshChatAlways", "CompletionFreshChatAlways", {true: "[+] yes fresh", false: "[-] no, with history"}, this.bCompletionFreshChatAlways, (val)=>{
|
||||||
this.bCompletionFreshChatAlways = val;
|
this.bCompletionFreshChatAlways = val;
|
||||||
});
|
});
|
||||||
elDiv.appendChild(bb);
|
elDiv.appendChild(bb);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue