mirror of
https://github.com/ParisNeo/lollms-webui.git
synced 2025-01-30 08:03:57 +00:00
Major upgrade in backends structure. Now you can build your own backend
This commit is contained in:
parent
ddafde66d5
commit
917600f412
@ -215,8 +215,8 @@ Now you're ready to work!
|
|||||||
|
|
||||||
# Supported backends
|
# Supported backends
|
||||||
Two backends are now supported:
|
Two backends are now supported:
|
||||||
1 - The llama_cpp backend
|
1 - [The llama_cpp backend](https://github.com/nomic-ai/pygpt4all)
|
||||||
2 - The GPT-j backend
|
2 - [The GPT-j backend](https://github.com/marella/gpt4all-j)
|
||||||
3 - Hugging face's Transformers (under construction)
|
3 - Hugging face's Transformers (under construction)
|
||||||
|
|
||||||
# Supported models
|
# Supported models
|
||||||
|
4
app.py
4
app.py
@ -146,8 +146,8 @@ class Gpt4AllWebUI(GPT4AllAPI):
|
|||||||
)
|
)
|
||||||
|
|
||||||
def list_backends(self):
|
def list_backends(self):
|
||||||
backends_dir = Path('./pyGpt4All/backends') # replace with the actual path to the models folder
|
backends_dir = Path('./backends') # replace with the actual path to the models folder
|
||||||
backends = [f.stem for f in backends_dir.glob('*.py') if f.stem!="backend" and f.stem!="__init__"]
|
backends = [f.stem for f in backends_dir.iterdir() if f.is_dir()]
|
||||||
return jsonify(backends)
|
return jsonify(backends)
|
||||||
|
|
||||||
|
|
||||||
|
@ -10,7 +10,7 @@
|
|||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Callable
|
from typing import Callable
|
||||||
from gpt4allj import Model
|
from gpt4allj import Model
|
||||||
from pyGpt4All.backends.backend import GPTBackend
|
from pyGpt4All.backend import GPTBackend
|
||||||
|
|
||||||
__author__ = "parisneo"
|
__author__ = "parisneo"
|
||||||
__github__ = "https://github.com/nomic-ai/gpt4all-ui"
|
__github__ = "https://github.com/nomic-ai/gpt4all-ui"
|
@ -11,7 +11,7 @@ from pathlib import Path
|
|||||||
from typing import Callable
|
from typing import Callable
|
||||||
from transformers import AutoTokenizer
|
from transformers import AutoTokenizer
|
||||||
from transformers import AutoModelForCausalLM
|
from transformers import AutoModelForCausalLM
|
||||||
from pyGpt4All.backends.backend import GPTBackend
|
from pyGpt4All.backend import GPTBackend
|
||||||
|
|
||||||
__author__ = "parisneo"
|
__author__ = "parisneo"
|
||||||
__github__ = "https://github.com/nomic-ai/gpt4all-ui"
|
__github__ = "https://github.com/nomic-ai/gpt4all-ui"
|
@ -10,7 +10,7 @@
|
|||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Callable
|
from typing import Callable
|
||||||
from pyllamacpp.model import Model
|
from pyllamacpp.model import Model
|
||||||
from pyGpt4All.backends.backend import GPTBackend
|
from pyGpt4All.backend import GPTBackend
|
||||||
|
|
||||||
__author__ = "parisneo"
|
__author__ = "parisneo"
|
||||||
__github__ = "https://github.com/nomic-ai/gpt4all-ui"
|
__github__ = "https://github.com/nomic-ai/gpt4all-ui"
|
@ -46,7 +46,7 @@ class GPT4AllAPI():
|
|||||||
self.full_message_list = []
|
self.full_message_list = []
|
||||||
|
|
||||||
# Select backend
|
# Select backend
|
||||||
self.BACKENDS_LIST = {f.stem:f for f in (Path("pyGpt4All")/"backends").glob("*.py") if f.stem not in ["__init__","backend"]}
|
self.BACKENDS_LIST = {f.stem:f for f in Path("backends").iterdir() if f.is_dir()}
|
||||||
|
|
||||||
self.load_backend(self.BACKENDS_LIST[self.config["backend"]])
|
self.load_backend(self.BACKENDS_LIST[self.config["backend"]])
|
||||||
|
|
||||||
@ -86,7 +86,7 @@ class GPT4AllAPI():
|
|||||||
module_name = backend_path.stem
|
module_name = backend_path.stem
|
||||||
|
|
||||||
# use importlib to load the module from the file path
|
# use importlib to load the module from the file path
|
||||||
loader = importlib.machinery.SourceFileLoader(module_name, str(absolute_path))
|
loader = importlib.machinery.SourceFileLoader(module_name, str(absolute_path/"__init__.py"))
|
||||||
backend_module = loader.load_module()
|
backend_module = loader.load_module()
|
||||||
backend_class = getattr(backend_module, backend_module.backend_name)
|
backend_class = getattr(backend_module, backend_module.backend_name)
|
||||||
self.backend = backend_class
|
self.backend = backend_class
|
||||||
|
@ -5,4 +5,8 @@ pyyaml
|
|||||||
markdown
|
markdown
|
||||||
pyllamacpp==1.0.6
|
pyllamacpp==1.0.6
|
||||||
gpt4all-j==0.2.1
|
gpt4all-j==0.2.1
|
||||||
|
--find-links https://download.pytorch.org/whl/cu117
|
||||||
|
torch==2.0.0
|
||||||
|
torchvision
|
||||||
|
torchaudio
|
||||||
transformers
|
transformers
|
@ -14,119 +14,134 @@ function update_main(){
|
|||||||
});
|
});
|
||||||
|
|
||||||
})
|
})
|
||||||
userInput.addEventListener('keydown', function(event) {
|
|
||||||
if (event.shiftKey && event.key === 'Enter') {
|
|
||||||
event.preventDefault();
|
|
||||||
userInput.style.height = userInput.scrollHeight + 'px';
|
|
||||||
userInput.value += '\n';
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
chatForm.addEventListener('submit', event => {
|
|
||||||
event.preventDefault();
|
function submit_form(){
|
||||||
console.log("Submitting")
|
console.log("Submitting")
|
||||||
|
|
||||||
// get user input and clear input field
|
// get user input and clear input field
|
||||||
message = userInput.value;
|
message = userInput.value;
|
||||||
userInput.value = '';
|
userInput.value = '';
|
||||||
|
|
||||||
// add user message to chat window
|
// add user message to chat window
|
||||||
const sendbtn = document.querySelector("#submit-input")
|
const sendbtn = document.querySelector("#submit-input")
|
||||||
const waitAnimation = document.querySelector("#wait-animation")
|
const waitAnimation = document.querySelector("#wait-animation")
|
||||||
const stopGeneration = document.querySelector("#stop-generation")
|
const stopGeneration = document.querySelector("#stop-generation")
|
||||||
|
|
||||||
sendbtn.style.display="none";
|
sendbtn.style.display="none";
|
||||||
waitAnimation.style.display="block";
|
waitAnimation.style.display="block";
|
||||||
stopGeneration.style.display = "block";
|
stopGeneration.style.display = "block";
|
||||||
console.log("Sending message to bot")
|
console.log("Sending message to bot")
|
||||||
|
|
||||||
user_msg = addMessage('',message, 0, 0, can_edit=true);
|
user_msg = addMessage('',message, 0, 0, can_edit=true);
|
||||||
bot_msg = addMessage('', '', 0, 0, can_edit=true);
|
bot_msg = addMessage('', '', 0, 0, can_edit=true);
|
||||||
|
|
||||||
fetch('/generate', {
|
fetch('/generate', {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
headers: {
|
headers: {
|
||||||
'Content-Type': 'application/json'
|
'Content-Type': 'application/json'
|
||||||
},
|
},
|
||||||
body: JSON.stringify({ message })
|
body: JSON.stringify({ message })
|
||||||
}).then(function(response) {
|
}).then(function(response) {
|
||||||
const stream = new ReadableStream({
|
const stream = new ReadableStream({
|
||||||
start(controller) {
|
start(controller) {
|
||||||
const reader = response.body.getReader();
|
const reader = response.body.getReader();
|
||||||
function push() {
|
function push() {
|
||||||
reader.read().then(function(result) {
|
reader.read().then(function(result) {
|
||||||
if (result.done) {
|
if (result.done) {
|
||||||
sendbtn.style.display="block";
|
sendbtn.style.display="block";
|
||||||
waitAnimation.style.display="none";
|
waitAnimation.style.display="none";
|
||||||
stopGeneration.style.display = "none";
|
stopGeneration.style.display = "none";
|
||||||
console.log(result)
|
console.log(result)
|
||||||
controller.close();
|
controller.close();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
controller.enqueue(result.value);
|
controller.enqueue(result.value);
|
||||||
push();
|
push();
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
push();
|
push();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
const textDecoder = new TextDecoder();
|
const textDecoder = new TextDecoder();
|
||||||
const readableStreamDefaultReader = stream.getReader();
|
const readableStreamDefaultReader = stream.getReader();
|
||||||
let entry_counter = 0
|
let entry_counter = 0
|
||||||
function readStream() {
|
function readStream() {
|
||||||
readableStreamDefaultReader.read().then(function(result) {
|
readableStreamDefaultReader.read().then(function(result) {
|
||||||
if (result.done) {
|
if (result.done) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
text = textDecoder.decode(result.value);
|
|
||||||
|
|
||||||
// The server will first send a json containing information about the message just sent
|
|
||||||
if(entry_counter==0)
|
|
||||||
{
|
|
||||||
// We parse it and
|
|
||||||
infos = JSON.parse(text);
|
|
||||||
|
|
||||||
user_msg.setSender(infos.user);
|
text = textDecoder.decode(result.value);
|
||||||
user_msg.setMessage(infos.message);
|
|
||||||
user_msg.setID(infos.id);
|
|
||||||
bot_msg.setSender(infos.bot);
|
|
||||||
bot_msg.setID(infos.response_id);
|
|
||||||
|
|
||||||
bot_msg.messageTextElement;
|
// The server will first send a json containing information about the message just sent
|
||||||
bot_msg.hiddenElement;
|
if(entry_counter==0)
|
||||||
entry_counter ++;
|
{
|
||||||
|
// We parse it and
|
||||||
|
infos = JSON.parse(text);
|
||||||
|
|
||||||
|
user_msg.setSender(infos.user);
|
||||||
|
user_msg.setMessage(infos.message);
|
||||||
|
user_msg.setID(infos.id);
|
||||||
|
bot_msg.setSender(infos.bot);
|
||||||
|
bot_msg.setID(infos.response_id);
|
||||||
|
|
||||||
|
bot_msg.messageTextElement;
|
||||||
|
bot_msg.hiddenElement;
|
||||||
|
entry_counter ++;
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
entry_counter ++;
|
||||||
|
prefix = "FINAL:";
|
||||||
|
if(text.startsWith(prefix)){
|
||||||
|
text = text.substring(prefix.length);
|
||||||
|
bot_msg.hiddenElement.innerHTML = text
|
||||||
|
bot_msg.messageTextElement.innerHTML = text
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
entry_counter ++;
|
// For the other enrtries, these are just the text of the chatbot
|
||||||
prefix = "FINAL:";
|
for (const char of text) {
|
||||||
if(text.startsWith(prefix)){
|
txt = bot_msg.hiddenElement.innerHTML;
|
||||||
text = text.substring(prefix.length);
|
if (char != '\f') {
|
||||||
bot_msg.hiddenElement.innerHTML = text
|
txt += char
|
||||||
bot_msg.messageTextElement.innerHTML = text
|
bot_msg.hiddenElement.innerHTML = txt;
|
||||||
}
|
bot_msg.messageTextElement.innerHTML = txt;
|
||||||
else{
|
}
|
||||||
// For the other enrtries, these are just the text of the chatbot
|
|
||||||
for (const char of text) {
|
|
||||||
txt = bot_msg.hiddenElement.innerHTML;
|
|
||||||
if (char != '\f') {
|
|
||||||
txt += char
|
|
||||||
bot_msg.hiddenElement.innerHTML = txt;
|
|
||||||
bot_msg.messageTextElement.innerHTML = txt;
|
|
||||||
}
|
|
||||||
|
|
||||||
// scroll to bottom of chat window
|
// scroll to bottom of chat window
|
||||||
chatWindow.scrollTop = chatWindow.scrollHeight;
|
chatWindow.scrollTop = chatWindow.scrollHeight;
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
readStream();
|
}
|
||||||
});
|
}
|
||||||
}
|
|
||||||
readStream();
|
readStream();
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
readStream();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
chatForm.addEventListener('submit', event => {
|
||||||
|
event.preventDefault();
|
||||||
|
submit_form();
|
||||||
});
|
});
|
||||||
|
userInput.addEventListener("keyup", function(event) {
|
||||||
|
// Check if Enter key was pressed while holding Shift
|
||||||
|
// Also check if Shift + Ctrl keys were pressed while typing
|
||||||
|
// These combinations override the submit action
|
||||||
|
const shiftPressed = event.shiftKey;
|
||||||
|
const ctrlPressed = event.ctrlKey && !event.metaKey;
|
||||||
|
|
||||||
|
if ((!shiftPressed) && event.key === "Enter") {
|
||||||
|
submit_form();
|
||||||
|
}
|
||||||
|
// Restore original functionality for the remaining cases
|
||||||
|
else if (!shiftPressed && ctrlPressed) {
|
||||||
|
setTimeout(() => {
|
||||||
|
userInput.focus();
|
||||||
|
contentEditable.value += event.data;
|
||||||
|
lastValue.innerHTML = userInput.value;
|
||||||
|
}, 0);
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
@ -35,7 +35,7 @@
|
|||||||
<div class="w-full flex justify-center">
|
<div class="w-full flex justify-center">
|
||||||
<div class="w-full flex bottom-0 fixed rounded-sm shadow shadow-white bg-gray-300 p-1 dark:bg-gray-500 flex-wrap">
|
<div class="w-full flex bottom-0 fixed rounded-sm shadow shadow-white bg-gray-300 p-1 dark:bg-gray-500 flex-wrap">
|
||||||
<form id="chat-form" class="w-full flex-row text-white mr-15 p-15">
|
<form id="chat-form" class="w-full flex-row text-white mr-15 p-15">
|
||||||
<input type="text" id="user-input" placeholder="Type your message..." class="dark:bg-gray-600 pl-1 pr-1 py-1 my-1 mr-2 text-black dark:text-white outline-none drop-shadow-sm w-full rounded-md flex-1">
|
<textarea type="text" id="user-input" placeholder="Type your message..." class="dark:bg-gray-600 pl-1 pr-1 py-1 my-1 mr-2 text-black dark:text-white outline-none drop-shadow-sm w-full rounded-md flex-1"></textarea>
|
||||||
<div id="wait-animation" style="display: none;" class="lds-facebook bg-secondary my-1 mx-1 outline-none drop-shadow-sm w-full rounded-md p-2"><div></div><div></div><div></div></div>
|
<div id="wait-animation" style="display: none;" class="lds-facebook bg-secondary my-1 mx-1 outline-none drop-shadow-sm w-full rounded-md p-2"><div></div><div></div><div></div></div>
|
||||||
<button id="stop-generation" style="display: none;" class="my-1 mx-1 outline-none px-4 dark:bg-gray-900 text-black dark:text-white rounded-md hover:bg-[#7ba0ea] active:bg-[#3d73e1] transition-colors ease-in-out">Stop generating</button>
|
<button id="stop-generation" style="display: none;" class="my-1 mx-1 outline-none px-4 dark:bg-gray-900 text-black dark:text-white rounded-md hover:bg-[#7ba0ea] active:bg-[#3d73e1] transition-colors ease-in-out">Stop generating</button>
|
||||||
<input type="submit" value="Send" id="submit-input" class="my-1 mx-1 outline-none px-4 dark:bg-gray-900 text-black dark:text-white rounded-md hover:bg-[#7ba0ea] active:bg-[#3d73e1] transition-colors ease-in-out">
|
<input type="submit" value="Send" id="submit-input" class="my-1 mx-1 outline-none px-4 dark:bg-gray-900 text-black dark:text-white rounded-md hover:bg-[#7ba0ea] active:bg-[#3d73e1] transition-colors ease-in-out">
|
||||||
|
Loading…
x
Reference in New Issue
Block a user