This commit is contained in:
Saifeddine ALOUI 2023-07-04 01:49:06 +02:00
parent 21f336bcdc
commit 60b116d4b8
11 changed files with 595 additions and 530 deletions

View File

@ -180,7 +180,7 @@ Events generated:
- Creates a deep copy of the configuration (`self.config`) and assigns it to `self.cp_config`.
- Sets the `"model_name"` property of `self.cp_config` to the selected model name.
- Tries to create an instance of the binding class (`self.binding`) with `self.cp_config`.
- If successful, assigns the created binding instance to `self.active_model`.
- If successful, assigns the created binding instance to `self.model`.
- Emits a `'select_model'` event with a success response, indicating that the model selection was successful.
- Returns and exits the function.
- If an exception occurs during model creation, prints the exception and emits a `'select_model'` event with a failure response, indicating that a binding needs to be selected first.

2
lollms/.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
logs
uploads

157
lollms/app.py Normal file
View File

@ -0,0 +1,157 @@
from lollms.main_config import LOLLMSConfig
from lollms.helpers import ASCIIColors
from lollms.paths import LollmsPaths
from lollms.personality import PersonalityBuilder
from lollms.binding import LLMBinding, BindingBuilder, ModelBuilder
from lollms.config import InstallOption
import traceback
from lollms.terminal import MainMenu
class LollmsApplication:
def __init__(self, app_name:str, config:LOLLMSConfig, lollms_paths:LollmsPaths) -> None:
"""
Creates a LOLLMS Application
"""
self.app_name = app_name
self.config = config
self.lollms_paths = lollms_paths
self.menu = MainMenu(self)
self.mounted_personalities = []
self.personality = None
if self.config.binding_name is None:
ASCIIColors.warning(f"No binding selected")
ASCIIColors.info("Please select a valid model or install a new one from a url")
self.menu.select_binding()
try:
self.binding = self.load_binding()
except Exception as ex:
ASCIIColors.error(f"Failed to load binding.\nReturned exception: {ex}")
if self.binding is not None:
if self.config.model_name is None:
ASCIIColors.warning(f"No model selected")
print("Please select a valid binding")
self.menu.select_model()
try:
self.model = self.load_model()
except Exception as ex:
ASCIIColors.error(f"Failed to load model.\nReturned exception: {ex}")
self.mount_personalities()
def trace_exception(self, ex):
# Catch the exception and get the traceback as a list of strings
traceback_lines = traceback.format_exception(type(ex), ex, ex.__traceback__)
# Join the traceback lines into a single string
traceback_text = ''.join(traceback_lines)
ASCIIColors.error(traceback_text)
def load_binding(self):
try:
binding = BindingBuilder().build_binding(self.config, self.lollms_paths)
except Exception as ex:
print(ex)
print(f"Couldn't find binding. Please verify your configuration file at {self.configuration_path} or use the next menu to select a valid binding")
print(f"Trying to reinstall binding")
binding = BindingBuilder().build_binding(self.config, self.lollms_paths,installation_option=InstallOption.FORCE_INSTALL)
return binding
def load_model(self):
try:
model = ModelBuilder(self.binding).get_model()
for personality in self.mounted_personalities:
if personality is not None:
personality.model = model
except Exception as ex:
ASCIIColors.error(f"Couldn't load model. Please verify your configuration file at {self.lollms_paths.personal_configuration_path} or use the next menu to select a valid model")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_model_path_infos()}")
print("Please select a valid model or install a new one from a url")
model = None
return model
def mount_personality(self, id:int):
try:
self.personality = PersonalityBuilder(self.lollms_paths, self.config, self.model).build_personality(id)
self.config.active_personality_id=len(self.config.personalities)-1
if self.personality.model is not None:
self.cond_tk = self.personality.model.tokenize(self.personality.personality_conditioning)
self.n_cond_tk = len(self.cond_tk)
ASCIIColors.success(f"Personality {self.personality.name} mounted successfully")
else:
ASCIIColors.success(f"Personality {self.personality.name} mounted successfully but no model is selected")
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality. Please verify your configuration file at {self.lollms_paths.personal_configuration_path} or use the next menu to select a valid personality")
ASCIIColors.error(f"Binding returned this exception : {ex}")
self.trace_exception(ex)
ASCIIColors.error(f"{self.config.get_personality_path_infos()}")
self.personality = None
self.mounted_personalities.append(self.personality)
return self.personality
def mount_personalities(self):
self.mounted_personalities = []
to_remove = []
for i in range(len(self.config["personalities"])):
p = self.mount_personality(i)
if p is None:
to_remove.append(i)
to_remove.sort(reverse=True)
for i in to_remove:
self.unmount_personality(i)
def unmount_personality(self, id:int)->bool:
if id<len(self.config.personalities):
del self.config.personalities[id]
del self.mounted_personalities[id]
if self.config.active_personality_id>=id:
self.config.active_personality_id-=1
self.config.save_config()
return True
else:
return False
def select_personality(self, id:int):
if id<len(self.config.personalities):
self.config.active_personality_id = id
self.personality = self.mount_personalities[id]
self.config.save_config()
return True
else:
return False
def load_personality(self):
try:
personality = PersonalityBuilder(self.lollms_paths, self.config, self.model).build_personality()
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality. Please verify your configuration file at {self.configuration_path} or use the next menu to select a valid personality")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_personality_path_infos()}")
print("Please select a valid model or install a new one from a url")
personality = None
return personality
@staticmethod
def reset_paths(lollms_paths:LollmsPaths):
lollms_paths.resetPaths()
@staticmethod
def reset_all_installs(lollms_paths:LollmsPaths):
ASCIIColors.info("Removeing all configuration files to force reinstall")
ASCIIColors.info(f"Searching files from {lollms_paths.personal_configuration_path}")
for file_path in lollms_paths.personal_configuration_path.iterdir():
if file_path.name!=f"{lollms_paths.tool_prefix}local_config.yaml" and file_path.suffix.lower()==".yaml":
file_path.unlink()
ASCIIColors.info(f"Deleted file: {file_path}")

View File

@ -4,269 +4,14 @@ from lollms.personality import MSG_TYPE, PersonalityBuilder
from lollms.main_config import LOLLMSConfig
from lollms.helpers import ASCIIColors
from lollms.paths import LollmsPaths
from lollms.app import LollmsApplication
from lollms.terminal import MainMenu
from pathlib import Path
from tqdm import tqdm
import pkg_resources
import argparse
import yaml
import sys
class LollmsApplication:
def __init__(self, config:LOLLMSConfig, lollms_paths:LollmsPaths) -> None:
self.config = config
self.lollms_paths = lollms_paths
def load_binding(self):
pass
def load_model(self):
pass
def load_personality(self):
pass
def reset_paths(lollms_paths:LollmsPaths):
lollms_paths.resetPaths()
def reset_all_installs(lollms_paths:LollmsPaths):
ASCIIColors.info("Removeing all configuration files to force reinstall")
ASCIIColors.info(f"Searching files from {lollms_paths.personal_configuration_path}")
for file_path in lollms_paths.personal_configuration_path.iterdir():
if file_path.name!=f"{lollms_paths.tool_prefix}local_config.yaml" and file_path.suffix.lower()==".yaml":
file_path.unlink()
ASCIIColors.info(f"Deleted file: {file_path}")
class MainMenu:
def __init__(self, lollms_app:LollmsApplication):
self.binding_infs = []
self.lollms_app = lollms_app
def show_logo(self):
print(f"{ASCIIColors.color_bright_yellow}")
print(" ___ ___ ___ ___ ___ ___ ")
print(" /\__\ /\ \ /\__\ /\__\ /\__\ /\ \ ")
print(" /:/ / /::\ \ /:/ / /:/ / /::| | /::\ \ ")
print(" /:/ / /:/\:\ \ /:/ / /:/ / /:|:| | /:/\ \ \ ")
print(" /:/ / /:/ \:\ \ /:/ / /:/ / /:/|:|__|__ _\:\~\ \ \ ")
print(" /:/__/ /:/__/ \:\__\ /:/__/ /:/__/ /:/ |::::\__\ /\ \:\ \ \__\ ")
print(" \:\ \ \:\ \ /:/ / \:\ \ \:\ \ \/__/~~/:/ / \:\ \:\ \/__/ ")
print(" \:\ \ \:\ /:/ / \:\ \ \:\ \ /:/ / \:\ \:\__\ ")
print(" \:\ \ \:\/:/ / \:\ \ \:\ \ /:/ / \:\/:/ / ")
print(" \:\__\ \::/ / \:\__\ \:\__\ /:/ / \::/ / ")
print(" \/__/ \/__/ \/__/ \/__/ \/__/ \/__/ ")
print(f"{ASCIIColors.color_reset}")
print(f"{ASCIIColors.color_red}Version: {ASCIIColors.color_green}{pkg_resources.get_distribution('lollms').version}")
print(f"{ASCIIColors.color_red}By : {ASCIIColors.color_green}ParisNeo")
print(f"{ASCIIColors.color_reset}")
def show_commands_list(self):
print()
print("Commands:")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} menu: shows main menu")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} help: shows this info")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} reset: resets the context")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} <empty prompt>: forces the model to continue generating")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} context_infos: current context size and space left before cropping")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} start_log: starts logging the discussion to a text file")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} stop_log: stops logging the discussion to a text file")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} send_file: uploads a file to the AI")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} exit: exists the console")
if self.lollms_app.personality.help !="":
print(f"Personality help:")
print(f"{self.lollms_app.personality.help}")
def show_menu(self, options):
print("Menu:")
for index, option in enumerate(options):
print(f"{ASCIIColors.color_green}{index + 1} -{ASCIIColors.color_reset} {option}")
choice = input("Enter your choice: ")
return int(choice) if choice.isdigit() else -1
def select_binding(self):
bindings_list = []
print()
print(f"{ASCIIColors.color_green}Current binding: {ASCIIColors.color_reset}{self.lollms_app.config['binding_name']}")
for p in self.lollms_app.lollms_paths.bindings_zoo_path.iterdir():
if p.is_dir() and not p.stem.startswith("."):
with open(p/"binding_card.yaml", "r") as f:
card = yaml.safe_load(f)
with open(p/"models.yaml", "r") as f:
models = yaml.safe_load(f)
is_installed = (self.lollms_app.lollms_paths.personal_configuration_path/f"binding_{p.name}.yaml").exists()
entry=f"{ASCIIColors.color_green if is_installed else ''}{'*' if self.lollms_app.config['binding_name']==card['name'] else ''} {card['name']} (by {card['author']})"
bindings_list.append(entry)
entry={
"name":p.name,
"card":card,
"models":models,
"installed": is_installed
}
self.binding_infs.append(entry)
bindings_list += ["Back"]
choice = self.show_menu(bindings_list)
if 1 <= choice <= len(bindings_list)-1:
print(f"You selected binding: {ASCIIColors.color_green}{self.binding_infs[choice - 1]['name']}{ASCIIColors.color_reset}")
self.lollms_app.config['binding_name']=self.binding_infs[choice - 1]['name']
self.lollms_app.load_binding()
self.lollms_app.config['model_name']=None
self.lollms_app.config.save_config()
elif choice <= len(bindings_list):
return
else:
print("Invalid choice!")
def select_model(self):
print()
print(f"{ASCIIColors.color_green}Current binding: {ASCIIColors.color_reset}{self.lollms_app.config['binding_name']}")
print(f"{ASCIIColors.color_green}Current model: {ASCIIColors.color_reset}{self.lollms_app.config['model_name']}")
models_dir:Path = (self.lollms_app.lollms_paths.personal_models_path/self.lollms_app.config['binding_name'])
models_dir.mkdir(parents=True, exist_ok=True)
models_list = [v for v in self.lollms_app.binding.list_models(self.lollms_app.config)] + ["Install model", "Change binding", "Back"]
choice = self.show_menu(models_list)
if 1 <= choice <= len(models_list)-3:
print(f"You selected model: {ASCIIColors.color_green}{models_list[choice - 1]}{ASCIIColors.color_reset}")
self.lollms_app.config['model_name']=models_list[choice - 1]
self.lollms_app.config.save_config()
self.lollms_app.load_model()
elif choice <= len(models_list)-2:
self.install_model()
elif choice <= len(models_list)-1:
self.select_binding()
self.select_model()
elif choice <= len(models_list):
return
else:
print("Invalid choice!")
def install_model(self):
models_list = ["Install model from internet","Install model from local file","Back"]
choice = self.show_menu(models_list)
if 1 <= choice <= len(models_list)-2:
url = input("Give a URL to the model to be downloaded :")
def progress_callback(blocks, block_size, total_size):
tqdm_bar.total=total_size
tqdm_bar.update(block_size)
# Usage example
with tqdm(total=100, unit="%", desc="Download Progress", ncols=80) as tqdm_bar:
self.lollms_app.config.download_model(url,self.lollms_app.binding, progress_callback)
self.select_model()
elif choice <= len(models_list)-1:
path = Path(input("Give a path to the model to be used on your PC:"))
if path.exists():
self.lollms_app.config.reference_model(path)
self.select_model()
elif choice <= len(models_list):
return
else:
print("Invalid choice!")
def select_personality(self):
print()
print(f"{ASCIIColors.color_green}Current personality: {ASCIIColors.color_reset}{self.lollms_app.config['personalities'][self.lollms_app.config['active_personality_id']]}")
personality_languages = [p.stem for p in self.lollms_app.lollms_paths.personalities_zoo_path.iterdir() if p.is_dir()] + ["Back"]
print("Select language")
choice = self.show_menu(personality_languages)
if 1 <= choice <= len(personality_languages)-1:
language = personality_languages[choice - 1]
print(f"You selected language: {ASCIIColors.color_green}{language}{ASCIIColors.color_reset}")
personality_categories = [p.stem for p in (self.lollms_app.lollms_paths.personalities_zoo_path/language).iterdir() if p.is_dir()]+["Back"]
print("Select category")
choice = self.show_menu(personality_categories)
if 1 <= choice <= len(personality_categories)-1:
category = personality_categories[choice - 1]
print(f"You selected category: {ASCIIColors.color_green}{category}{ASCIIColors.color_reset}")
personality_names = [p.stem for p in (self.lollms_app.lollms_paths.personalities_zoo_path/language/category).iterdir() if p.is_dir()]+["Back"]
print("Select personality")
choice = self.show_menu(personality_names)
if 1 <= choice <= len(personality_names)-1:
name = personality_names[choice - 1]
print(f"You selected personality: {ASCIIColors.color_green}{name}{ASCIIColors.color_reset}")
self.lollms_app.config["personalities"]=[f"{language}/{category}/{name}"]
self.lollms_app.load_personality()
self.lollms_app.config.save_config()
print("Personality saved successfully!")
elif 1 <= choice <= len(personality_names):
return
else:
print("Invalid choice!")
elif 1 <= choice <= len(personality_categories):
return
else:
print("Invalid choice!")
elif 1 <= choice <= len(personality_languages):
return
else:
print("Invalid choice!")
def reinstall_binding(self):
lollms_app = self.lollms_app
try:
lollms_app.binding = BindingBuilder().build_binding(lollms_app.config, lollms_app.lollms_paths,InstallOption.FORCE_INSTALL)
except Exception as ex:
print(ex)
print(f"Couldn't find binding. Please verify your configuration file at {lollms_app.config.file_path} or use the next menu to select a valid binding")
self.select_binding()
def reinstall_personality(self):
lollms_app = self.lollms_app
try:
lollms_app.personality = PersonalityBuilder(lollms_app.lollms_paths, lollms_app.config, lollms_app.model, installation_option=InstallOption.FORCE_INSTALL).build_personality()
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality. Please verify your configuration file at {lollms_app.configuration_path} or use the next menu to select a valid personality")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{lollms_app.config.get_personality_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.select_model()
def main_menu(self):
while True:
print("\nMain Menu:")
print(f"{ASCIIColors.color_green}1 -{ASCIIColors.color_reset} Select Binding")
print(f"{ASCIIColors.color_green}2 -{ASCIIColors.color_reset} Select Model")
print(f"{ASCIIColors.color_green}3 -{ASCIIColors.color_reset} Select Personality")
print(f"{ASCIIColors.color_green}4 -{ASCIIColors.color_reset} Reinstall current Binding")
print(f"{ASCIIColors.color_green}5 -{ASCIIColors.color_reset} Reinstall current Personality")
print(f"{ASCIIColors.color_green}6 -{ASCIIColors.color_reset} Reset all installs")
print(f"{ASCIIColors.color_green}7 -{ASCIIColors.color_reset} Reset paths")
print(f"{ASCIIColors.color_green}0 -{ASCIIColors.color_reset} Back to app")
print(f"{ASCIIColors.color_green}-1 -{ASCIIColors.color_reset} Help")
print(f"{ASCIIColors.color_green}-2 -{ASCIIColors.color_reset} Exit app")
choice = input("Enter your choice: ").strip()
if choice == "1":
self.select_binding()
elif choice == "2":
self.select_model()
elif choice == "3":
self.select_personality()
elif choice == "4":
self.reinstall_binding()
elif choice == "5":
self.reinstall_personality()
elif choice == "6":
reset_all_installs()
elif choice == "6":
reset_paths()
elif choice == "0":
print("Back to main app...")
break
elif choice == "-1":
self.show_commands_list()
elif choice == "-2":
print("Bye")
sys.exit(0)
else:
print("Invalid choice! Try again.")
class Conversation(LollmsApplication):
def __init__(
self,
@ -277,42 +22,20 @@ class Conversation(LollmsApplication):
show_model_infos:bool=True,
show_welcome_message:bool=True
):
# Fore it to be a path
self.configuration_path = configuration_path
self.is_logging = False
self.log_file_path = ""
self.bot_says = ""
# get paths
lollms_paths = LollmsPaths.find_paths(force_local=False, tool_prefix="lollms_server_")
# Configuration loading part
config = LOLLMSConfig.autoload(lollms_paths, configuration_path)
super().__init__(config, lollms_paths=lollms_paths)
# Build menu
self.menu = MainMenu(self)
# load binding
self.load_binding()
if self.config.model_name is None:
self.menu.select_model()
# Load model
self.load_model()
# cfg.binding_name = llm_binding.binding_folder_name
# cfg.model_name = model_name
# Load personality
try:
self.load_personality()
except Exception as ex:
print(f"No personality selected. Please select one from the zoo. {ex}")
self.menu.select_personality()
super().__init__("lollms-console",config, lollms_paths)
if show_logo:
self.menu.show_logo()
@ -321,18 +44,21 @@ class Conversation(LollmsApplication):
if show_personality_infos:
print()
print(f"{ASCIIColors.color_green}-----------------------------------------------------------------")
print(f"{ASCIIColors.color_green}Current personality : {ASCIIColors.color_reset}{self.personality}")
print(f"{ASCIIColors.color_green}Version : {ASCIIColors.color_reset}{self.personality.version}")
print(f"{ASCIIColors.color_green}Author : {ASCIIColors.color_reset}{self.personality.author}")
print(f"{ASCIIColors.color_green}Description : {ASCIIColors.color_reset}{self.personality.personality_description}")
print(f"{ASCIIColors.color_green}-----------------------------------------------------------------")
print()
if show_model_infos:
print()
print(f"{ASCIIColors.color_green}-----------------------------------------------------------------")
print(f"{ASCIIColors.color_green}Current binding : {ASCIIColors.color_reset}{self.config['binding_name']}")
print(f"{ASCIIColors.color_green}Current model : {ASCIIColors.color_reset}{self.config['model_name']}")
print(f"{ASCIIColors.color_green}Personal data path : {ASCIIColors.color_reset}{self.lollms_paths.personal_path}")
print(f"{ASCIIColors.color_green}-----------------------------------------------------------------")
print()
@ -398,45 +124,6 @@ Participating personalities:
def load_binding(self):
if self.config.binding_name is None:
print(f"No bounding selected")
print("Please select a valid model or install a new one from a url")
self.menu.select_binding()
# cfg.download_model(url)
else:
try:
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths)
except Exception as ex:
print(ex)
print(f"Couldn't find binding. Please verify your configuration file at {self.configuration_path} or use the next menu to select a valid binding")
print(f"Trying to reinstall binding")
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths,installation_option=InstallOption.FORCE_INSTALL)
self.menu.select_binding()
def load_model(self):
try:
self.model = ModelBuilder(self.binding).get_model()
except Exception as ex:
ASCIIColors.error(f"Couldn't load model. Please verify your configuration file at {self.configuration_path} or use the next menu to select a valid model")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_model_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.menu.select_model()
def load_personality(self):
try:
self.personality = PersonalityBuilder(self.lollms_paths, self.config, self.model).build_personality()
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality. Please verify your configuration file at {self.configuration_path} or use the next menu to select a valid personality")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_personality_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.menu.select_model()
self.cond_tk = self.personality.model.tokenize(self.personality.personality_conditioning)
self.n_cond_tk = len(self.cond_tk)
def reset_context(self):
if self.personality.include_welcome_message_in_disucssion:
full_discussion = (
@ -605,7 +292,7 @@ def main():
args = parser.parse_args()
if args.reset_installs:
reset_all_installs()
LollmsApplication.reset_all_installs()
if args.reset_personal_path:
LollmsPaths.reset_configs()

40
lollms/extension.py Normal file
View File

@ -0,0 +1,40 @@
# File : extension.py
# Author : ParisNeo
# Description :
# This is the main class to be imported by the extension
# it gives your code access to the model, the callback functions, the model conditionning etc
from lollms.helpers import ASCIIColors
from lollms.config import BaseConfig
from enum import Enum
__author__ = "parisneo"
__github__ = "https://github.com/ParisNeo/lollms-webui"
__copyright__ = "Copyright 2023, "
__license__ = "Apache 2.0"
class EXTENSION_TYPE(Enum):
EXTENSION_TYPE_STAND_ALONE = 0 # An extension that has access to the current personality and model but has an independant
class Extension():
def __init__(self, metadata_file_path:str, app) -> None:
self.app = app
self.metadata_file_path = metadata_file_path
self.config = BaseConfig(file_path=metadata_file_path)
self.config.load_config()
def install(self):
"""
Installation procedure (to be implemented)
"""
ASCIIColors.blue("*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*")
ASCIIColors.red(f"Installing {self.binding_folder_name}")
ASCIIColors.blue("*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*")
def get_ui():
"""
Get user interface of the extension
"""
return "<p>This is a ui extension template</p>"

View File

@ -74,6 +74,15 @@ class LollmsPaths:
self.personal_log_path.mkdir(parents=True, exist_ok=True)
self.personal_uploads_path.mkdir(parents=True, exist_ok=True)
if not self.bindings_zoo_path.exists():
# Clone the repository to the target path
ASCIIColors.info("No bindings found in your personal space.\nCloning the personalities zoo")
subprocess.run(["git", "clone", bindings_zoo_repo, self.bindings_zoo_path])
else:
# Pull the repository if it already exists
ASCIIColors.info("Bindings zoo found in your personal space.\nPulling last personalities zoo")
subprocess.run(["git", "-C", self.bindings_zoo_path, "pull"])
if not self.personalities_zoo_path.exists():
# Clone the repository to the target path
ASCIIColors.info("No personalities found in your personal space.\nCloning the personalities zoo")
@ -83,15 +92,6 @@ class LollmsPaths:
ASCIIColors.info("Personalities zoo found in your personal space.\nPulling last personalities zoo")
subprocess.run(["git", "-C", self.personalities_zoo_path, "pull"])
if not self.bindings_zoo_path.exists():
# Clone the repository to the target path
ASCIIColors.info("No personalities found in your personal space.\nCloning the personalities zoo")
subprocess.run(["git", "clone", bindings_zoo_repo, self.bindings_zoo_path])
else:
# Pull the repository if it already exists
ASCIIColors.info("Personalities zoo found in your personal space.\nPulling last personalities zoo")
subprocess.run(["git", "-C", self.bindings_zoo_path, "pull"])
def copy_default_config(self):
local_config_path = self.personal_configuration_path / f"{self.tool_prefix}local_config.yaml"

View File

@ -1072,13 +1072,19 @@ class PersonalityBuilder:
self.installation_option = installation_option
def build_personality(self):
if self.config["active_personality_id"]>=len(self.config["personalities"]):
ASCIIColors.warning("Personality ID was out of range. Resetting to 0.")
self.config["active_personality_id"]=0
if len(self.config["personalities"][self.config["active_personality_id"]].split("/"))==3:
def build_personality(self, id:int=None):
if id is None:
id = self.config["active_personality_id"]
if self.config["active_personality_id"]>=len(self.config["personalities"]):
ASCIIColors.warning("Personality ID was out of range. Resetting to 0.")
self.config["active_personality_id"]=0
id = 0
else:
if id>len(self.config["personalities"]):
id = len(self.config["personalities"])-1
if len(self.config["personalities"][id].split("/"))==3:
self.personality = AIPersonality(
self.lollms_paths.personalities_zoo_path / self.config["personalities"][self.config["active_personality_id"]],
self.lollms_paths.personalities_zoo_path / self.config["personalities"][id],
self.lollms_paths,
self.config,
self.model,
@ -1086,7 +1092,7 @@ class PersonalityBuilder:
)
else:
self.personality = AIPersonality(
self.config["personalities"][self.config["active_personality_id"]],
self.config["personalities"][id],
self.lollms_paths,
self.config,
self.model,

View File

@ -11,6 +11,7 @@ from lollms.helpers import ASCIIColors
from lollms.console import MainMenu
from lollms.paths import LollmsPaths
from lollms.console import MainMenu
from lollms.app import LollmsApplication
from typing import List, Tuple
import importlib
from pathlib import Path
@ -28,39 +29,24 @@ def reset_all_installs(lollms_paths:LollmsPaths):
ASCIIColors.info(f"Deleted file: {file_path}")
class LoLLMsServer:
class LoLLMsServer(LollmsApplication):
def __init__(self):
host = "localhost"
port = "9601"
self.clients = {}
self.current_binding = None
self.active_model = None
self.model = None
self.personalities = []
self.answer = ['']
self.is_ready = True
self.lollms_paths = LollmsPaths.find_paths(force_local=False, tool_prefix="lollms_server_")
self.menu = MainMenu(self)
parser = argparse.ArgumentParser()
parser.add_argument('--host', '-hst', default=host, help='Host name')
parser.add_argument('--port', '-prt', default=port, help='Port number')
parser.add_argument('--config', '-cfg', default=None, help='Path to the configuration file')
parser.add_argument('--bindings_path', '-bp', default=str(self.lollms_paths.bindings_zoo_path),
help='The path to the Bindings folder')
parser.add_argument('--personalities_path', '-pp',
default=str(self.lollms_paths.personalities_zoo_path),
help='The path to the personalities folder')
parser.add_argument('--models_path', '-mp', default=str(self.lollms_paths.personal_models_path),
help='The path to the models folder')
parser.add_argument('--binding_name', '-b', default=None,
help='Binding to be used by default')
parser.add_argument('--model_name', '-m', default=None,
help='Model name')
parser.add_argument('--personality_full_name', '-p', default="personality",
help='Personality path relative to the personalities folder (language/category/name)')
parser.add_argument('--reset_personal_path', action='store_true', help='Reset the personal path')
parser.add_argument('--reset_config', action='store_true', help='Reset the configurations')
@ -70,7 +56,7 @@ class LoLLMsServer:
args = parser.parse_args()
if args.reset_installs:
reset_all_installs()
self.reset_all_installs()
if args.reset_personal_path:
LollmsPaths.reset_configs()
@ -83,50 +69,15 @@ class LoLLMsServer:
ASCIIColors.success("LOLLMS configuration reset successfully")
except:
ASCIIColors.success("Couldn't reset LOLLMS configuration")
else:
lollms_paths = LollmsPaths.find_paths(force_local=False, tool_prefix="lollms_server_")
# Configuration loading part
self.config = LOLLMSConfig.autoload(self.lollms_paths, args.config)
config = LOLLMSConfig.autoload(lollms_paths, None)
if args.binding_name:
self.config.binding_name = args.binding_name
if args.model_name:
self.config.model_name = args.model_name
# Recover bindings path
self.personalities_path = Path(args.personalities_path)
self.bindings_path = Path(args.bindings_path)
self.models_path = Path(args.models_path)
if self.config.binding_name is None:
self.menu.select_binding()
else:
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths)
if self.config.model_name is None:
self.menu.select_model()
else:
try:
self.active_model = self.binding.build_model()
except Exception as ex:
print(f"{ASCIIColors.color_red}Couldn't load model Please select a valid model{ASCIIColors.color_reset}")
print(f"{ASCIIColors.color_red}{ex}{ASCIIColors.color_reset}")
self.menu.select_model()
for p in self.config.personalities:
personality = AIPersonality(
self.config.lollms_paths.personalities_zoo_path/p,
self.lollms_paths,
self.config,
self.active_model
)
self.personalities.append(personality)
if self.config.active_personality_id>len(self.personalities):
self.config.active_personality_id = 0
self.active_personality = self.personalities[self.config.active_personality_id]
super().__init__("lollms-server", config, lollms_paths)
self.menu.show_logo()
self.app = Flask("LoLLMsServer")
#self.app.config['SECRET_KEY'] = 'lollmssecret'
CORS(self.app) # Enable CORS for all routes
@ -144,45 +95,6 @@ class LoLLMsServer:
self.run(args.host, args.port)
def load_binding(self):
if self.config.binding_name is None:
print(f"No bounding selected")
print("Please select a valid model or install a new one from a url")
self.menu.select_binding()
# cfg.download_model(url)
else:
try:
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths)
except Exception as ex:
print(ex)
print(f"Couldn't find binding. Please verify your configuration file at {self.config.file_path} or use the next menu to select a valid binding")
print(f"Trying to reinstall binding")
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths, InstallOption.FORCE_INSTALL)
self.menu.select_binding()
def load_model(self):
try:
self.active_model = ModelBuilder(self.binding).get_model()
ASCIIColors.success("Model loaded successfully")
except Exception as ex:
ASCIIColors.error(f"Couldn't load model.")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_model_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.menu.select_model()
def load_personality(self):
try:
self.personality = PersonalityBuilder(self.lollms_paths, self.config, self.model).build_personality()
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality.")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_personality_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.menu.select_model()
self.cond_tk = self.personality.model.tokenize(self.personality.personality_conditioning)
self.n_cond_tk = len(self.cond_tk)
def initialize_routes(self):
@self.socketio.on('connect')
def handle_connect():
@ -369,7 +281,7 @@ class LoLLMsServer:
self.cp_config = copy.deepcopy(self.config)
self.cp_config["model_name"] = data['model_name']
try:
self.active_model = self.binding.build_model()
self.model = self.binding.build_model()
emit('select_model', {'success':True, 'model_name': model_name}, room=request.sid)
except Exception as ex:
print(ex)
@ -383,7 +295,7 @@ class LoLLMsServer:
personality_path,
self.lollms_paths,
self.config,
self.active_model
self.model
)
self.personalities.append(personality)
self.config["personalities"].append(personality_path)
@ -413,13 +325,13 @@ class LoLLMsServer:
@self.socketio.on('tokenize')
def tokenize(data):
prompt = data['prompt']
tk = self.active_model.tokenize(prompt)
tk = self.model.tokenize(prompt)
emit("tokenized", {"tokens":tk})
@self.socketio.on('detokenize')
def detokenize(data):
prompt = data['prompt']
txt = self.active_model.detokenize(prompt)
txt = self.model.detokenize(prompt)
emit("detokenized", {"text":txt})
@self.socketio.on('cancel_generation')
@ -442,7 +354,7 @@ class LoLLMsServer:
return
def generate_text():
self.is_ready = False
model = self.active_model
model = self.model
self.clients[client_id]["is_generating"]=True
self.clients[client_id]["requested_stop"]=False
prompt = data['prompt']
@ -462,7 +374,7 @@ class LoLLMsServer:
self.answer = {"full_text":""}
def callback(text, message_type: MSG_TYPE):
if message_type == MSG_TYPE.MSG_TYPE_CHUNK:
ASCIIColors.success(f"generated:{len(self.answer['full_text'])} words", end='\r')
ASCIIColors.success(f"generated:{len(self.answer['full_text'].split())} words", end='\r')
self.answer["full_text"] = self.answer["full_text"] + text
self.socketio.emit('text_chunk', {'chunk': text, 'type':MSG_TYPE.MSG_TYPE_CHUNK.value}, room=client_id)
self.socketio.sleep(0)
@ -479,8 +391,10 @@ class LoLLMsServer:
fd = model.detokenize(tk[-min(self.config.ctx_size-n_predicts,n_tokens):])
try:
ASCIIColors.print("warm up", ASCIIColors.color_bright_cyan)
generated_text = model.generate(fd, n_predict=n_predicts, callback=callback,
ASCIIColors.print("warming up", ASCIIColors.color_bright_cyan)
generated_text = model.generate(fd,
n_predict=n_predicts,
callback=callback,
temperature = parameters["temperature"],
top_k = parameters["top_k"],
top_p = parameters["top_p"],
@ -588,7 +502,7 @@ class LoLLMsServer:
def run(self, host="localhost", port="9601"):
print(f"{ASCIIColors.color_red}Current binding (model) : {ASCIIColors.color_reset}{self.binding}")
print(f"{ASCIIColors.color_red}Current personality : {ASCIIColors.color_reset}{self.active_personality}")
print(f"{ASCIIColors.color_red}Current personality : {ASCIIColors.color_reset}{self.config.personalities[self.config.active_personality_id]}")
ASCIIColors.info(f"Serving on address: http://{host}:{port}")
self.socketio.run(self.app, host=host, port=port)

View File

@ -9,17 +9,11 @@ import argparse
from tqdm import tqdm
from lollms.personality import PersonalityBuilder
from lollms.console import MainMenu
def reset_all_installs(lollms_paths:LollmsPaths):
ASCIIColors.info("Removeing all configuration files to force reinstall")
ASCIIColors.info(f"Searching files from {lollms_paths.personal_configuration_path}")
for file_path in lollms_paths.personal_configuration_path.iterdir():
if file_path.name!=f"{lollms_paths.tool_prefix}local_config.yaml" and file_path.suffix.lower()==".yaml":
file_path.unlink()
ASCIIColors.info(f"Deleted file: {file_path}")
from lollms.app import LollmsApplication
class Settings:
class Settings(LollmsApplication):
def __init__(
self,
configuration_path:str|Path=None,
@ -29,46 +23,16 @@ class Settings:
show_model_infos:bool=True,
show_welcome_message:bool=True
):
# Fore it to be a path
self.is_logging = False
self.log_file_path = ""
self.bot_says = ""
# get paths
self.lollms_paths = LollmsPaths.find_paths(force_local=False, tool_prefix="lollms_server_")
lollms_paths = LollmsPaths.find_paths(force_local=False, tool_prefix="lollms_server_")
ASCIIColors.yellow("------ Lollms Paths ------")
ASCIIColors.info(self.lollms_paths)
ASCIIColors.info(lollms_paths)
ASCIIColors.yellow("------ ------------ ------")
# Load maoin configuration
config = LOLLMSConfig.autoload(lollms_paths)
# Build menu
self.menu = MainMenu(self)
# Change configuration
original = self.lollms_paths.default_cfg_path
if configuration_path is None:
local = self.lollms_paths.personal_configuration_path / f"{self.lollms_paths.tool_prefix}local_config.yaml"
else:
local = Path(configuration_path)
if not local.exists():
shutil.copy(original, local)
self.cfg_path = local
self.config = LOLLMSConfig(self.cfg_path, self.lollms_paths)
# load binding
if self.config.binding_name is not None:
self.load_binding()
# Load model
if self.config.model_name is not None:
self.load_model()
# Load personality
try:
self.load_personality()
except Exception as ex:
print(f"No personality selected. Please select one from the zoo. {ex}")
self.menu.select_personality()
super().__init__("lollms-settings", config, lollms_paths)
if show_logo:
self.menu.show_logo()
@ -145,43 +109,6 @@ Participating personalities:
self.is_logging = False
def load_binding(self):
if self.config.binding_name is None:
print(f"No bounding selected")
print("Please select a valid model or install a new one from a url")
self.menu.select_binding()
# cfg.download_model(url)
else:
try:
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths)
except Exception as ex:
print(ex)
print(f"Couldn't find binding. Please verify your configuration file at {self.cfg_path} or use the next menu to select a valid binding")
print(f"Trying to reinstall binding")
self.binding = BindingBuilder().build_binding(self.config, self.lollms_paths,installation_option=InstallOption.FORCE_INSTALL)
self.menu.select_binding()
def load_model(self):
try:
self.model = ModelBuilder(self.binding).get_model()
except Exception as ex:
ASCIIColors.error(f"Couldn't load model. Please verify your configuration file at {self.cfg_path} or use the next menu to select a valid model")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_model_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.menu.select_model()
def load_personality(self):
try:
self.personality = PersonalityBuilder(self.lollms_paths, self.config, self.model).build_personality()
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality. Please verify your configuration file at {self.cfg_path} or use the next menu to select a valid personality")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{self.config.get_personality_path_infos()}")
print("Please select a valid model or install a new one from a url")
def reset_context(self):
if self.personality.include_welcome_message_in_disucssion:
full_discussion = (
@ -248,7 +175,7 @@ def main():
args = parser.parse_args()
if args.reset_installs:
reset_all_installs()
LollmsApplication.reset_all_installs()
if args.reset_personal_path:
LollmsPaths.reset_configs()

332
lollms/terminal.py Normal file
View File

@ -0,0 +1,332 @@
from lollms.helpers import ASCIIColors
from typing import TYPE_CHECKING
if TYPE_CHECKING:
from lollms.app import LollmsApplication
from lollms.binding import BindingBuilder
from lollms.config import InstallOption
from lollms.personality import PersonalityBuilder
from tqdm import tqdm
import pkg_resources
from pathlib import Path
import yaml
import sys
class MainMenu:
def __init__(self, lollms_app:'LollmsApplication'):
self.binding_infs = []
self.lollms_app = lollms_app
def show_logo(self):
print(f"{ASCIIColors.color_bright_yellow}")
print(" ___ ___ ___ ___ ___ ___ ")
print(" /\__\ /\ \ /\__\ /\__\ /\__\ /\ \ ")
print(" /:/ / /::\ \ /:/ / /:/ / /::| | /::\ \ ")
print(" /:/ / /:/\:\ \ /:/ / /:/ / /:|:| | /:/\ \ \ ")
print(" /:/ / /:/ \:\ \ /:/ / /:/ / /:/|:|__|__ _\:\~\ \ \ ")
print(" /:/__/ /:/__/ \:\__\ /:/__/ /:/__/ /:/ |::::\__\ /\ \:\ \ \__\ ")
print(" \:\ \ \:\ \ /:/ / \:\ \ \:\ \ \/__/~~/:/ / \:\ \:\ \/__/ ")
print(" \:\ \ \:\ /:/ / \:\ \ \:\ \ /:/ / \:\ \:\__\ ")
print(" \:\ \ \:\/:/ / \:\ \ \:\ \ /:/ / \:\/:/ / ")
print(" \:\__\ \::/ / \:\__\ \:\__\ /:/ / \::/ / ")
print(" \/__/ \/__/ \/__/ \/__/ \/__/ \/__/ ")
print(f"{ASCIIColors.color_reset}")
print(f"{ASCIIColors.color_red}Version: {ASCIIColors.color_green}{pkg_resources.get_distribution('lollms').version}")
print(f"{ASCIIColors.color_red}By : {ASCIIColors.color_green}ParisNeo")
print(f"{ASCIIColors.color_reset}")
def show_commands_list(self):
print()
print("Commands:")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} menu: shows main menu")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} help: shows this info")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} reset: resets the context")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} <empty prompt>: forces the model to continue generating")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} context_infos: current context size and space left before cropping")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} start_log: starts logging the discussion to a text file")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} stop_log: stops logging the discussion to a text file")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} send_file: uploads a file to the AI")
print(f" {ASCIIColors.color_red}{ASCIIColors.color_reset} exit: exists the console")
if self.lollms_app.personality:
if self.lollms_app.personality.help !="":
print(f"Personality help:")
print(f"{self.lollms_app.personality.help}")
def show_menu(self, options, title="Menu:", selection:int=None):
ASCIIColors.yellow(title)
for index, option in enumerate(options):
if selection is not None and index==selection:
print(f"{ASCIIColors.color_green}{index + 1} - {option}{ASCIIColors.color_reset}")
else:
print(f"{ASCIIColors.color_green}{index + 1} -{ASCIIColors.color_reset} {option}")
choice = input("Enter your choice: ")
return int(choice) if choice.isdigit() else -1
def select_binding(self):
bindings_list = []
print()
print(f"{ASCIIColors.color_green}Current binding: {ASCIIColors.color_reset}{self.lollms_app.config['binding_name']}")
for p in self.lollms_app.lollms_paths.bindings_zoo_path.iterdir():
if p.is_dir() and not p.stem.startswith("."):
with open(p/"binding_card.yaml", "r") as f:
card = yaml.safe_load(f)
with open(p/"models.yaml", "r") as f:
models = yaml.safe_load(f)
is_installed = (self.lollms_app.lollms_paths.personal_configuration_path/f"binding_{p.name}.yaml").exists()
entry=f"{ASCIIColors.color_green if is_installed else ''}{'*' if self.lollms_app.config['binding_name']==card['name'] else ''} {card['name']} (by {card['author']})"
bindings_list.append(entry)
entry={
"name":p.name,
"card":card,
"models":models,
"installed": is_installed
}
self.binding_infs.append(entry)
bindings_list += ["Back"]
choice = self.show_menu(bindings_list)
if 1 <= choice <= len(bindings_list)-1:
print(f"You selected binding: {ASCIIColors.color_green}{self.binding_infs[choice - 1]['name']}{ASCIIColors.color_reset}")
self.lollms_app.config['binding_name']=self.binding_infs[choice - 1]['name']
self.lollms_app.load_binding()
self.lollms_app.config['model_name']=None
self.lollms_app.config.save_config()
elif choice <= len(bindings_list):
return
else:
print("Invalid choice!")
def select_model(self):
print()
print(f"{ASCIIColors.color_green}Current binding: {ASCIIColors.color_reset}{self.lollms_app.config['binding_name']}")
print(f"{ASCIIColors.color_green}Current model: {ASCIIColors.color_reset}{self.lollms_app.config['model_name']}")
models_dir:Path = (self.lollms_app.lollms_paths.personal_models_path/self.lollms_app.config['binding_name'])
models_dir.mkdir(parents=True, exist_ok=True)
models_list = [v for v in self.lollms_app.binding.list_models(self.lollms_app.config)] + ["Install model", "Change binding", "Back"]
choice = self.show_menu(models_list)
if 1 <= choice <= len(models_list)-3:
print(f"You selected model: {ASCIIColors.color_green}{models_list[choice - 1]}{ASCIIColors.color_reset}")
self.lollms_app.config['model_name']=models_list[choice - 1]
self.lollms_app.config.save_config()
self.lollms_app.load_model()
elif choice <= len(models_list)-2:
self.install_model()
elif choice <= len(models_list)-1:
self.select_binding()
self.select_model()
elif choice <= len(models_list):
return
else:
print("Invalid choice!")
def install_model(self):
models_list = ["Install model from internet","Install model from local file","Back"]
choice = self.show_menu(models_list)
if 1 <= choice <= len(models_list)-2:
url = input("Give a URL to the model to be downloaded :")
def progress_callback(blocks, block_size, total_size):
tqdm_bar.total=total_size
tqdm_bar.update(block_size)
# Usage example
with tqdm(total=100, unit="%", desc="Download Progress", ncols=80) as tqdm_bar:
self.lollms_app.config.download_model(url,self.lollms_app.binding, progress_callback)
self.select_model()
elif choice <= len(models_list)-1:
path = Path(input("Give a path to the model to be used on your PC:"))
if path.exists():
self.lollms_app.config.reference_model(path)
self.select_model()
elif choice <= len(models_list):
return
else:
print("Invalid choice!")
def mount_personality(self):
print()
ASCIIColors.red(f"Mounted personalities:")
for i,personality in enumerate(self.lollms_app.config['personalities']):
if i==self.lollms_app.config['active_personality_id']:
ASCIIColors.green(personality)
else:
ASCIIColors.yellow(personality)
personality_languages = [p.stem for p in self.lollms_app.lollms_paths.personalities_zoo_path.iterdir() if p.is_dir() and not p.name.startswith(".")] + ["Back"]
print("Select language")
choice = self.show_menu(personality_languages)
if 1 <= choice <= len(personality_languages)-1:
language = personality_languages[choice - 1]
print(f"You selected language: {ASCIIColors.color_green}{language}{ASCIIColors.color_reset}")
personality_categories = [p.stem for p in (self.lollms_app.lollms_paths.personalities_zoo_path/language).iterdir() if p.is_dir() and not p.name.startswith(".")]+["Back"]
print("Select category")
choice = self.show_menu(personality_categories)
if 1 <= choice <= len(personality_categories)-1:
category = personality_categories[choice - 1]
print(f"You selected category: {ASCIIColors.color_green}{category}{ASCIIColors.color_reset}")
personality_names = [p.stem for p in (self.lollms_app.lollms_paths.personalities_zoo_path/language/category).iterdir() if p.is_dir() and not p.name.startswith(".")]+["Back"]
print("Select personality")
choice = self.show_menu(personality_names)
if 1 <= choice <= len(personality_names)-1:
name = personality_names[choice - 1]
print(f"You selected personality: {ASCIIColors.color_green}{name}{ASCIIColors.color_reset}")
self.lollms_app.config["personalities"].append(f"{language}/{category}/{name}")
self.lollms_app.mount_personality(len(self.lollms_app.config["personalities"])-1)
self.lollms_app.config.save_config()
print("Personality mounted successfully!")
elif 1 <= choice <= len(personality_names):
return
else:
print("Invalid choice!")
elif 1 <= choice <= len(personality_categories):
return
else:
print("Invalid choice!")
elif 1 <= choice <= len(personality_languages):
return
else:
print("Invalid choice!")
def vew_mounted_personalities(self):
ASCIIColors.info("Here is the list of mounted personalities")
entries = self.lollms_app.config['personalities']
for id, entry in enumerate(entries):
if id != self.lollms_app.config.active_personality_id:
ASCIIColors.yellow(f"{id+1} - {entry}")
else:
ASCIIColors.green(f"{id+1} - {entry}")
self.show_menu(["Back"])
def unmount_personality(self):
ASCIIColors.info("Select personality to unmount")
entries = self.lollms_app.config['personalities']+["Back"]
try:
choice = int(self.show_menu(entries, self.lollms_app.config['active_personality_id']))-1
if choice<len(entries)-1:
self.lollms_app.unmount_personality(choice)
except Exception as ex:
ASCIIColors.error(f"Couldn't uhnmount personality.\nGot this exception:{ex}")
def select_personality(self):
ASCIIColors.info("Select personality to activate")
entries = self.lollms_app.config['personalities']+["Back"]
try:
choice = int(self.show_menu(entries, self.lollms_app.config['active_personality_id']))-1
if choice<len(entries)-1:
self.lollms_app.select_personality(choice)
except Exception as ex:
ASCIIColors.error(f"Couldn't set personality.\nGot this exception:{ex}")
def reinstall_binding(self):
lollms_app = self.lollms_app
bindings_list = []
print()
print(f"{ASCIIColors.color_green}Current binding: {ASCIIColors.color_reset}{self.lollms_app.config['binding_name']}")
for p in self.lollms_app.lollms_paths.bindings_zoo_path.iterdir():
if p.is_dir() and not p.stem.startswith("."):
with open(p/"binding_card.yaml", "r") as f:
card = yaml.safe_load(f)
with open(p/"models.yaml", "r") as f:
models = yaml.safe_load(f)
is_installed = (self.lollms_app.lollms_paths.personal_configuration_path/f"binding_{p.name}.yaml").exists()
entry=f"{ASCIIColors.color_green if is_installed else ''}{'*' if self.lollms_app.config['binding_name']==card['name'] else ''} {card['name']} (by {card['author']})"
bindings_list.append(entry)
entry={
"name":p.name,
"card":card,
"models":models,
"installed": is_installed
}
self.binding_infs.append(entry)
bindings_list += ["Back"]
choice = self.show_menu(bindings_list)
if 1 <= choice <= len(bindings_list)-1:
print(f"You selected binding: {ASCIIColors.color_green}{self.binding_infs[choice - 1]['name']}{ASCIIColors.color_reset}")
self.lollms_app.config['binding_name']=self.binding_infs[choice - 1]['name']
try:
lollms_app.binding = BindingBuilder().build_binding(lollms_app.config, lollms_app.lollms_paths,InstallOption.FORCE_INSTALL)
except Exception as ex:
print(ex)
print(f"Couldn't find binding. Please verify your configuration file at {lollms_app.config.file_path} or use the next menu to select a valid binding")
self.select_binding()
self.lollms_app.config['model_name']=None
self.lollms_app.config.save_config()
elif choice <= len(bindings_list):
return
else:
print("Invalid choice!")
def reinstall_personality(self):
lollms_app = self.lollms_app
try:
lollms_app.personality = PersonalityBuilder(lollms_app.lollms_paths, lollms_app.config, lollms_app.model, installation_option=InstallOption.FORCE_INSTALL).build_personality()
except Exception as ex:
ASCIIColors.error(f"Couldn't load personality. Please verify your configuration file at {lollms_app.configuration_path} or use the next menu to select a valid personality")
ASCIIColors.error(f"Binding returned this exception : {ex}")
ASCIIColors.error(f"{lollms_app.config.get_personality_path_infos()}")
print("Please select a valid model or install a new one from a url")
self.select_model()
def main_menu(self):
while True:
print("\nMain Menu:")
print(f"{ASCIIColors.color_green}1 -{ASCIIColors.color_reset} Select Binding")
print(f"{ASCIIColors.color_green}2 -{ASCIIColors.color_reset} Select Model")
print(f"{ASCIIColors.color_green}3 -{ASCIIColors.color_reset} View mounted Personalities")
print(f"{ASCIIColors.color_green}4 -{ASCIIColors.color_reset} Mount Personality")
print(f"{ASCIIColors.color_green}5 -{ASCIIColors.color_reset} Unmount Personality")
print(f"{ASCIIColors.color_green}6 -{ASCIIColors.color_reset} Select Personality")
print(f"{ASCIIColors.color_green}7 -{ASCIIColors.color_reset} Reinstall Binding")
print(f"{ASCIIColors.color_green}8 -{ASCIIColors.color_reset} Reinstall current Personality")
print(f"{ASCIIColors.color_green}9 -{ASCIIColors.color_reset} Reset all installs")
print(f"{ASCIIColors.color_green}10 -{ASCIIColors.color_reset} Reset paths")
print(f"{ASCIIColors.color_green}11 -{ASCIIColors.color_reset} Back to app")
print(f"{ASCIIColors.color_green}12 -{ASCIIColors.color_reset} Help")
print(f"{ASCIIColors.color_green}13 -{ASCIIColors.color_reset} Exit app")
choice = input("Enter your choice: ").strip()
if choice == "1":
self.select_binding()
elif choice == "2":
self.select_model()
elif choice == "3":
self.vew_mounted_personalities()
elif choice == "4":
self.mount_personality()
elif choice == "5":
self.unmount_personality()
elif choice == "6":
self.select_personality()
elif choice == "7":
self.reinstall_binding()
elif choice == "8":
self.reinstall_personality()
elif choice == "9":
self.lollms_app.reset_all_installs()
elif choice == "10":
self.lollms_app.reset_paths()
elif choice == "11":
print("Back to main app...")
break
elif choice == "12":
self.show_commands_list()
elif choice == "13":
print("Bye")
sys.exit(0)
else:
print("Invalid choice! Try again.")

View File

@ -26,7 +26,7 @@ def get_all_files(path):
setuptools.setup(
name="lollms",
version="2.1.14",
version="2.1.15",
author="Saifeddine ALOUI",
author_email="aloui.saifeddine@gmail.com",
description="A python library for AI personality definition",