This commit is contained in:
wailovet
2024-06-05 02:44:41 +08:00
parent db7eaf2e15
commit 67068a9dbb
7 changed files with 657 additions and 43 deletions
+30 -1
View File
@@ -60,9 +60,12 @@ class MZ_LLamaCPPModelConfig_ManualSelect:
@classmethod
def INPUT_TYPES(s):
gguf_files = Utils.get_gguf_files()
chat_format = mz_llama_cpp.get_llama_cpp_chat_handlers()
return {
"required": {
"llama_cpp_model": (gguf_files,),
"chat_format": (["auto"] + chat_format, {"default": "auto"}),
},
"optional": {
},
@@ -82,9 +85,13 @@ class MZ_LLamaCPPModelConfig_ManualSelect:
llama_cpp_model = os.path.join(
Utils.get_gguf_models_path(), llama_cpp_model)
chat_format = kwargs.get("chat_format", "auto")
if chat_format == "auto":
chat_format = None
return ({
"type": "ManualSelect",
"model_path": llama_cpp_model,
"chat_format": chat_format,
},)
@@ -100,9 +107,11 @@ class MZ_LLamaCPPModelConfig_DownloaderSelect:
model_names = [
model["model"] for model in optional_models
]
chat_format = mz_llama_cpp.get_llama_cpp_chat_handlers()
return {
"required": {
"model_name": (model_names,),
"chat_format": (["auto"] + chat_format, {"default": "auto"}),
},
"optional": {
},
@@ -118,9 +127,13 @@ class MZ_LLamaCPPModelConfig_DownloaderSelect:
kwargs = kwargs.copy()
model_name = kwargs.get("model_name", "")
chat_format = kwargs.get("chat_format", "auto")
if chat_format == "auto":
chat_format = None
return ({
"type": "DownloaderSelect",
"model_name": model_name,
"chat_format": chat_format,
},)
@@ -211,6 +224,9 @@ class MZ_LLamaCPPOptions:
opt = {}
for key in kwargs:
opt[key] = kwargs[key]
# if opt.get("chat_format", None) == "auto":
# opt["chat_format"] = None
return (opt,)
@@ -370,6 +386,7 @@ class MZ_ImageInterrogatorCLIPTextEncode:
return {
"required": {
"resolution": ("INT", {"default": 512, "min": 128, "max": 0xffffffffffffffff}),
"post_processing": ([False, True], {"default": True}),
"keep_device": ([False, True], {"default": False}),
"seed": ("INT", {"default": 0, "min": 0, "max": 0xffffffffffffffff}),
},
@@ -406,10 +423,12 @@ class MZ_ImageInterrogatorModelConfig_ManualSelect:
@classmethod
def INPUT_TYPES(s):
gguf_files = Utils.get_gguf_files()
chat_format = mz_llama_cpp.get_llama_cpp_chat_handlers()
return {
"required": {
"llama_cpp_model": (gguf_files,),
"mmproj_model": (["auto"] + gguf_files,),
"chat_format": (["auto"] + chat_format, {"default": "auto"}),
},
"optional": {
},
@@ -434,10 +453,14 @@ class MZ_ImageInterrogatorModelConfig_ManualSelect:
mmproj_model = os.path.join(
Utils.get_gguf_models_path(), mmproj_model)
chat_format = kwargs.get("chat_format", "auto")
if chat_format == "auto":
chat_format = None
return ({
"type": "ManualSelect",
"model_path": llama_cpp_model,
"mmproj_model": mmproj_model,
"chat_format": chat_format,
},)
@@ -459,10 +482,12 @@ class MZ_ImageInterrogatorModelConfig_DownloaderSelect:
model["model"] for model in optional_models
]
chat_format = mz_llama_cpp.get_llama_cpp_chat_handlers()
return {
"required": {
"model_name": (model_names,),
"mmproj_model_name": (mmproj_model_names,),
"mmproj_model_name": (["auto"] + mmproj_model_names,),
"chat_format": (["auto"] + chat_format, {"default": "auto"}),
},
"optional": {
},
@@ -478,10 +503,14 @@ class MZ_ImageInterrogatorModelConfig_DownloaderSelect:
kwargs = kwargs.copy()
model_name = kwargs.get("model_name")
mmproj_model_name = kwargs.get("mmproj_model_name", "auto")
chat_format = kwargs.get("chat_format", "auto")
if chat_format == "auto":
chat_format = None
return ({
"type": "DownloaderSelect",
"model_name": model_name,
"mmproj_model_name": mmproj_model_name,
"chat_format": chat_format,
},)
+349
View File
@@ -0,0 +1,349 @@
# coding=utf8
import json
from typing import Any, List, NamedTuple, Optional, Tuple
import json.decoder
from json.decoder import JSONDecodeError as PyJSONDecodeError, JSONDecoder, py_scanstring
from json.scanner import py_make_scanner
from typing import Any, Dict, NamedTuple, Optional, Tuple, Union
class FixResult(NamedTuple):
success: bool
line: str
origin: bool
class JSONFixer:
def __init__(self, max_try: int = 20, max_stack: int = 3, *, js_style: bool = False) -> None:
self._max_try = max_try
self._max_stack = max_stack
self._js_style = js_style
self.last_fix: Optional[bool] = None
self.fix_stack: List[str] = []
def fix(self, line: str, *, strict: bool = True) -> FixResult:
try:
json.loads(line, strict=strict)
return FixResult(success=True, line=line, origin=True)
except Exception:
pass
ok, new_line = self.fixwithtry(line, strict=strict)
return FixResult(success=ok, line=new_line, origin=False)
def fixwithtry(self, line: str, *, strict: bool = True) -> Tuple[bool, str]:
if self._max_try <= 0:
return False, line
self.fix_stack = []
self.last_fix = None
ok = False
for _ in range(self._max_try):
ok, new_line = self.patch_line(line, strict=strict)
if ok:
return ok, new_line
self.last_fix = line != new_line
if self.last_fix:
self.fix_stack.insert(0, new_line)
self.fix_stack = self.fix_stack[: self._max_stack]
line = new_line
return ok, line
def patch_line(self, line: str, *, strict: bool = True) -> Tuple[bool, str]:
result = decode_line(line, strict=strict)
if result.success:
return True, line
if isinstance(result.exception, ValueError):
return self.patch_value_error(line, result.err_info)
if isinstance(result.exception, StopIteration):
return self.patch_stop_iteration(line)
if result.exception is None:
return self.patch_half_parse(line, result.err_info)
return False, line
def patch_value_error(self, line: str, err_info: Any) -> Tuple[bool, str]:
if err_info["error"] is None:
return False, line
error = err_info["error"]
pos = err_info["pos"]
nextchar = line[pos: pos + 1]
lastchar = line[pos - 1: pos]
nextline = line[pos:]
lastline = line[:pos]
if error == errors.StringUnterminatedString:
return False, insert_line(line, '"', len(line))
if error == errors.ObjectExceptKey:
if nextchar == "":
return False, insert_line(line, "}", pos)
if nextchar == ":":
return False, insert_line(line, '""', pos)
if lastchar in "{," and nextchar == ",":
return False, remove_line(line, pos, pos + 1)
if lastchar == "," and nextchar == "}":
return False, remove_line(line, pos - 1, pos)
if nextchar in "[{":
return False, insert_line(line, '"":', pos)
if self._js_style:
# find 'abc'
if nextchar == "'":
nextline = remove_line(nextline, 0, 1)
idx = nextline.find(":")
if idx != -1 and idx != 0 and nextline[idx - 1] == "'":
nextline = remove_line(nextline, idx - 1, idx)
return False, lastline + nextline
# abc:1 --> "aabc":1
idx = nextline.find(":")
if idx != -1:
line = lastline + insert_line(nextline, '"', idx)
return False, insert_line(line, '"', pos)
# TODO process more case "
return False, insert_line(line, '"', pos)
if error == errors.ObjectExceptColon:
return False, insert_line(line, ":", pos)
if error == errors.ObjectExceptObject:
if nextchar == "":
if lastchar == "{":
return False, insert_line(line, "}", pos)
return False, insert_line(line, "null}", pos)
if nextchar == "}":
return False, insert_line(line, "null", pos)
# TODO guess more
return False, insert_line(line, '"', pos)
if error == errors.ObjectExceptComma:
if nextchar == "":
return False, insert_line(line, "}", pos)
return False, insert_line(line, ",", pos)
if error == errors.ArrayExceptObject:
if nextchar == "," and lastchar == "[":
return False, remove_line(line, pos, pos + 1)
if nextchar == ",":
return False, insert_line(line, "null", pos)
if nextchar == "]":
return False, remove_line(line, pos - 1, pos)
if nextchar == "":
if lastchar == "[":
return False, insert_line(line, "]", pos)
return False, insert_line(line, "null]", pos)
# TODO guess more?
return False, insert_line(line, "{", pos)
if error == errors.ArrayExceptComma:
if len(line) == pos:
return False, insert_line(line, "]", pos)
return False, insert_line(line, ",", pos)
# TODO unknonwn
return False, line
def patch_stop_iteration(self, line: str) -> Tuple[bool, str]:
# TODO clean
# TODO fix
# 1. }]
# 2. ]}
# 3. constans
# 4. -
# 先 patch 完 {[]}
# TODO: process number
if line.startswith("-."):
new_line = "-0." + line[2:]
return False, new_line
# patch
left = patch_lastest_left_object_and_array(line)
if left == "":
if not self.last_fix:
left = patch_guess_left(line)
new_line = left + line
return False, new_line
def patch_half_parse(self, line: str, err_info: Any) -> Tuple[bool, str]:
obj, end = err_info
nextline = line[end:].strip()
nextchar = nextline[:1]
left = patch_lastest_left_object_and_array(nextline)
# ??
if left == "":
if nextchar == ",":
left = "["
elif nextchar == ":" and isinstance(obj, str):
left = "{"
else:
if not self.last_fix:
left = patch_guess_left(nextline)
new_line = left + line[:end] + nextline
return False, new_line
# TODO better name
def patch_lastest_left_object_and_array(line: str) -> str:
# '}]{[' --> '[{}]{['
pairs = {"}": "{", "]": "["}
breaks = "{["
left = ""
for char in line:
if char in breaks:
break
if char in pairs:
left = pairs[char] + left
return left
# TODO better name
# TODO 改成 lastest
# TODO {}}]]]] --> { not [
def patch_guess_left(line: str) -> str:
miss_object = line.count("}") - line.count("{")
miss_array = line.count("]") - line.count("[")
if miss_object == miss_array == 0:
if line[-1:] == '"' and line.count('"') == 1:
return '"'
elif miss_object >= miss_array:
return "{"
else:
return "["
return ""
def insert_line(line: str, value: str, pos: int) -> str:
return line[:pos] + value + line[pos:]
def remove_line(line: str, start: int, end: int) -> str:
return line[:start] + line[end:]
class JSONDecodeError:
def __init__(self, parser, message):
self.message = message
self.parser = parser
def __eq__(self, err):
return err.parser == self.parser and self.message in err.message
class errors:
StringInvalidUXXXXEscape = JSONDecodeError(
"py_scanstring", "Invalid \\uXXXX escape")
# 2 different case
StringUnterminatedString = JSONDecodeError(
"py_scanstring", "Unterminated string starting at")
StringInvalidControlCharacter = JSONDecodeError(
"py_scanstring", "Invalid control character")
StringInvalidEscape = JSONDecodeError("py_scanstring", "Invalid \\escape")
ObjectExceptColon = JSONDecodeError(
"JSONObject", "Expecting ':' delimiter")
ObjectExceptObject = JSONDecodeError("JSONObject", "Expecting value")
# 2 different case
ObjectExceptKey = JSONDecodeError(
"JSONObject", "Expecting property name enclosed in double quotes")
ObjectExceptComma = JSONDecodeError(
"JSONObject", "Expecting ',' delimiter")
ArrayExceptObject = JSONDecodeError("JSONArray", "Expecting value")
ArrayExceptComma = JSONDecodeError("JSONArray", "Expecting ',' delimiter")
@classmethod
def get_decode_error(cls, parser, message):
err = JSONDecodeError(parser, message)
for _, value in cls.__dict__.items():
if isinstance(value, JSONDecodeError):
if err == value:
return value
return None
"""
01 先不看,不研究
02 badcase: " --> "" success
03 控制符 pass
04 unicode \\u 的 pass
05 同上
06 object 后面没有跟随 " , badcase: {abc":1} --> {"abc":1}
07 object key 后面没有 : , badcase: {"abc"1} --> {"abc":1}
08 object 开始检测 Value 收到 StopIteration
08.1 要么后面没有了
08.2 要么后面不是 "/{/[/n[ull]/t[rue]/f[alse]/number/NaN/Infinity/-Infinity 开头的东西
-- 08.1 后面补上 null}
-- 08.2 无脑补一个 "
09 object 解析完一个 pair 后,下一个不是}, 期待一个 ','
badcase {"k":1"s":2}
10 在 09 的基础上解析完{"k":1, 发现下一个不是 ", 这个后面再优化(暂时和 06 一致)
badcase {"k":1,x":2}
11 array 开始检测 Value 收到 StopIteration
11.1 要么后面没有了,补上]
11.2 同 08.2,无脑补一个{ 看看
12 array 解析完前一个 object, 需要一个 ,
这里 nextchar 既不是 ] 也不是, 代表这个 nextchar 的 end 也已经+1 了,所以减 2
"""
def errmsg_inv(e: ValueError) -> Dict[str, Any]:
assert isinstance(e, PyJSONDecodeError)
parser = e.__dict__.get("parser", "")
errmsg = e.msg
localerr = errors.get_decode_error(parser, errmsg)
return {
"parsers": e.__dict__.get("parsers", []),
"error": localerr,
"lineno": e.lineno,
"colno": e.colno,
"pos": e.pos,
}
def record_parser_name(parser: Any) -> Any:
def new_parser(*args: Any, **kwargs: Any) -> Any:
try:
return parser(*args, **kwargs)
except Exception as e:
if "parser" not in e.__dict__:
e.__dict__["parser"] = parser.__name__
if "parsers" not in e.__dict__:
e.__dict__["parsers"] = []
e.__dict__["parsers"].append(parser.__name__)
raise e
return new_parser
def make_decoder(*, strict: bool = True) -> JSONDecoder:
json.decoder.scanstring = record_parser_name(py_scanstring)
decoder = JSONDecoder(strict=strict)
decoder.parse_object = record_parser_name(decoder.parse_object)
decoder.parse_array = record_parser_name(decoder.parse_array)
decoder.parse_string = record_parser_name(py_scanstring)
decoder.parse_object = record_parser_name(decoder.parse_object)
decoder.scan_once = py_make_scanner(decoder)
return decoder
decoder = make_decoder()
decoder_unstrict = make_decoder(strict=False)
class DecodeResult(NamedTuple):
success: bool
exception: Optional[Exception]
err_info: Optional[Union[Dict[str, Any], Tuple[Any, Any]]]
def decode_line(line: str, *, strict: bool = True) -> DecodeResult:
try:
obj, end = (decoder if strict else decoder_unstrict).scan_once(line, 0)
ok = end == len(line)
return DecodeResult(success=ok, exception=None, err_info=(obj, end))
except StopIteration as e:
return DecodeResult(success=False, exception=e, err_info=None)
except ValueError as e:
err_info = errmsg_inv(e)
return DecodeResult(success=False, exception=e, err_info=err_info)
+1
View File
@@ -35,6 +35,7 @@ ZH_Replace_Map = {
"ModelConfigManualSelect": "手动模型选择器",
"ModelConfigDownloaderSelect": "预设模型下载器",
"captioner_config": "打标器配置",
"post_processing": "后处理",
}
+141 -10
View File
@@ -56,16 +56,23 @@ def get_style_presets():
def llama_cpp_node_encode(args_dict):
importlib.reload(mz_prompts)
importlib.reload(mz_llama_cpp)
# importlib.reload(mz_prompt_utils)
model_config = args_dict.get("llama_cpp_model", {})
mz_prompt_utils.Utils.print_log(f"model_config: {model_config}")
chat_format = model_config.get("chat_format", None)
select_model_type = model_config.get("type", "ManualSelect")
if select_model_type == "ManualSelect":
model_file = model_config.get("model_path", "auto")
if model_file == "auto":
model_file = mz_prompt_utils.Utils.get_auto_model_fullpath(
"Meta-Llama-3-8B-Instruct.Q4_K_M")
if "llama-3" in mz_llama_cpp.get_llama_cpp_chat_handlers():
chat_format = "llama-3"
elif select_model_type == "DownloaderSelect":
model_name = model_config.get("model_name", "")
model_file = mz_prompt_utils.Utils.get_auto_model_fullpath(
@@ -81,6 +88,7 @@ def llama_cpp_node_encode(args_dict):
keep_device = args_dict.get("keep_device", False)
seed = args_dict.get("seed", -1)
options["seed"] = seed
options["chat_format"] = chat_format
customize_instruct = args_dict.get("customize_instruct", None)
mz_prompt_utils.Utils.print_log(
@@ -136,8 +144,19 @@ def llama_cpp_node_encode(args_dict):
schema=schema,
options=options,
)
try:
response_json = json.loads(response_text)
except Exception as e:
from . import half_json
print("json.loads failed, try fix response_text: ", response_text)
json_fixer = half_json.JSONFixer()
fix_resp = json_fixer.fix(response_text)
if fix_resp.success:
print("fix success, use fixed response_text: ", fix_resp.line)
response_json = json.loads(fix_resp.line)
else:
raise e
response_json = json.loads(response_text)
mz_prompt_utils.Utils.print_log(
f"response_json: {json.dumps(response_json, indent=2)}")
@@ -322,6 +341,8 @@ def image_interrogator_node_encode(args_dict):
"图片批量反推任务已完成 ; Image batch reverse push task completed")
model_config = args_dict.get("image_interrogator_model", {})
chat_format = model_config.get("chat_format", None)
llama_cpp_model = model_config.get("llama_cpp_model", "auto")
mmproj_model = model_config.get("mmproj_model", "auto")
@@ -401,13 +422,20 @@ def image_interrogator_node_encode(args_dict):
seed = args_dict.get("seed", -1)
options = args_dict.get("llama_cpp_options", {})
options["seed"] = seed
options["chat_format"] = chat_format
image = mz_prompt_utils.Utils.resize_max(image, resolution, resolution)
customize_instruct = args_dict.get("customize_instruct", None)
if customize_instruct is None:
system_prompt = mz_prompts.M_ImageCaptioner_System
question = mz_prompts.M_ImageCaptioner_Prompt
# system_prompt = mz_prompts.GPT4VImageCaptioner_System
# question = mz_prompts.GPT4VImageCaptioner_Prompt
# system_prompt = mz_prompts.M_ImageCaptioner2_System
# question = mz_prompts.M_ImageCaptioner2_Prompt
system_prompt = "You are an assistant who perfectly describes images."
question = "Describe this image in detail please."
else:
system_prompt = customize_instruct.get("system", "")
question = customize_instruct.get("instruct", "")
@@ -421,13 +449,116 @@ def image_interrogator_node_encode(args_dict):
system=system_prompt,
question=question,
)
if response is not None:
response = response.strip()
if customize_instruct is None:
# 去除开头的In the image,
start_text = "In the image, "
if response.startswith(start_text):
response = response[len(start_text):]
response = response.strip()
if response is not None and response != "":
if args_dict.get("post_processing", False):
# 双引号换成空格
response = response.replace("\"", " ")
# 中括号换成空格
response = response.replace("[", " ")
response = response.replace("]", " ")
# 括号换成空格
response = response.replace("(", " ")
response = response.replace(")", " ")
# 去除多余空格
while response.find(" ") != -1:
response = response.replace(" ", " ")
# 从第一个为英文字母的地方开始截取
for i in range(len(response)):
if response[i].isalpha():
response = response[i:]
break
response = response.strip()
schema = get_schema_obj(
keys_type={
"short_describes": get_schema_base_type("string"),
"subject_tags": get_schema_array("string"),
"action_tags": get_schema_array("string"),
"light_tags": get_schema_array("string"),
"scene_tags": get_schema_array("string"),
"mood_tags": get_schema_array("string"),
"style_tags": get_schema_array("string"),
"object_tags": get_schema_array("string"),
},
required=[
"short_describes",
"subject_tags",
"action_tags",
"lights_tags",
"scenes_tags",
"moods_tags",
"styles_tags",
"objects_tags",
]
)
response_json_str = mz_llama_cpp.llama_cpp_simple_interrogator_to_json(
model_file=llama_cpp_model,
system=mz_prompts.ImageCaptionerPostProcessing_System,
question=f"Content: {response}",
schema=schema,
options=options,
)
try:
response_json = json.loads(response_json_str)
except Exception as e:
from . import half_json
print("json.loads failed, try fix response_json_str: ",
response_json_str)
json_fixer = half_json.JSONFixer()
fix_resp = json_fixer.fix(response_json_str)
if fix_resp.success:
print("fix success, use fixed response_json_str: ",
fix_resp.line)
response_json = json.loads(fix_resp.line)
else:
raise e
responses = []
def pure_words(text: str) -> bool:
number_of_spaces = text.count(" ")
if number_of_spaces > 2:
return False
for c in text:
if not c.isalpha() and c != "-" and c != "_" and c != " ":
return False
return True
for key, value in response_json.items():
if type(value) == list:
# 去除开头.和空格
value = [v.strip().lstrip(".") for v in value]
# 去除空字符串
value = [v for v in value if v != ""]
# 去除带有空格和标点符号的字符串
value = [
v for v in value if pure_words(v)]
# 空格换成下划线
value = [v.replace(" ", "_") for v in value]
# 首字母小写
value = [v.lower() for v in value]
if len(value) > 0:
responses.append(f"{', '.join(value)}")
description = response_json.get("short_describes", "")
if description != "":
responses.append(f"{description}")
# 对response进行去重
response = ", ".join(responses)
if keep_device is False:
mz_llama_cpp.freed_gpu_memory(model_file=llama_cpp_model)
+42 -1
View File
@@ -1,3 +1,4 @@
import copy
import importlib
import json
import os
@@ -109,8 +110,19 @@ def check_llama_cpp_requirements():
print("llama_cpp installed successfully. (llama_cpp安装成功)")
def get_llama_cpp_chat_handlers():
check_llama_cpp_requirements()
from llama_cpp import llama_chat_format
chat_handlers = llama_chat_format.LlamaChatCompletionHandlerRegistry()._chat_handlers
chat_handlers = list(chat_handlers.keys())
return chat_handlers
def LlamaCppOptions():
# chat_handlers = ["auto"] + get_llama_cpp_chat_handlers()
return {
# "chat_format": chat_handlers,
"n_ctx": 2048,
"n_batch": 2048,
"n_threads": 0,
@@ -170,6 +182,9 @@ def llama_cpp_messages(model_file, mmproj_file=None, messages=[], options={}):
is_opts_changed = False
mz_prompt_utils.Utils.print_log(
f"llama_cpp_messages chat_format: {options.get('chat_format', None)}")
if model_and_opt is not None:
for opt in init_opts:
if model_and_opt.get("options").get(opt) != options.get(opt):
@@ -259,6 +274,25 @@ def llama_cpp_messages(model_file, mmproj_file=None, messages=[], options={}):
mirostat_mode = 1
elif options.get("mirostat_mode", "none") == "mirostat_v2":
mirostat_mode = 2
try:
debuf_messages = copy.deepcopy(messages)
for dindex in range(len(debuf_messages)):
if debuf_messages[dindex].get("role") == "user":
debuf_messages_content = debuf_messages[dindex].get(
"content", [])
if type(debuf_messages_content) != list:
continue
for ccindex in range(len(debuf_messages_content)):
if debuf_messages_content[ccindex].get("type") == "image_url":
debuf_messages[dindex]["content"][ccindex]["image_url"] = debuf_messages[
dindex]["content"][ccindex]["image_url"] = None
mz_prompt_utils.Utils.print_log(
f"LLAMA_CPP messages: {json.dumps(debuf_messages, indent=4, ensure_ascii=False)}")
except Exception as e:
mz_prompt_utils.Utils.print_log(
f"LLAMA_CPP messages: {messages}")
output = model.create_chat_completion(
messages=messages,
response_format=response_format,
@@ -276,6 +310,8 @@ def llama_cpp_messages(model_file, mmproj_file=None, messages=[], options={}):
mirostat_mode=mirostat_mode,
mirostat_tau=options.get("mirostat_tau", 5.0),
mirostat_eta=options.get("mirostat_eta", 0.1),
tools=options.get("tools", None),
tool_choice=options.get("tool_choice", None),
)
mz_prompt_utils.Utils.print_log(f"LLAMA_CPP: \n{output}")
choices = output.get("choices", [])
@@ -330,7 +366,9 @@ def llama_cpp_simple_interrogator_to_json(model_file, use_system=True, system=No
}
options["response_format"] = response_format
options["chat_format"] = "chatml"
# if options.get("chat_format", None) is None:
# options["chat_format"] = "llama-2"
result = llama_cpp_messages(model_file, None, messages, options=options)
result = result.replace("\n", " ")
@@ -385,6 +423,9 @@ def llava_cpp_messages(model_file, mmproj_file, messages, options={}):
options = options.copy()
options["logits_all"] = True
options["n_ctx"] = max(4096, options.get("n_ctx", 4096))
# if options.get("chat_format", None) is None:
# options["chat_format"] = "llama-2"
return llama_cpp_messages(model_file, mmproj_file, messages, options)
+74 -31
View File
@@ -172,41 +172,81 @@ class Utils:
os.makedirs(models_path, exist_ok=True)
return models_path
def translate_text(text, from_code, to_code):
def get_translate_object(from_code, to_code):
try:
import argostranslate
from argostranslate import translate
except ImportError:
subprocess.run([
sys.executable, "-m",
"pip", "install", "argostranslate"], check=True)
import argostranslate
from argostranslate import translate
is_disabel_argostranslate = Utils.cache_get(
"is_disabel_argostranslate")
try:
translation = translate.get_translation_from_codes(
from_code, to_code)
if translation is None:
raise Exception("Translation not found")
if is_disabel_argostranslate is not None:
return None
try:
import argostranslate
from argostranslate import translate, package
except ImportError:
subprocess.run([
sys.executable, "-m",
"pip", "install", "argostranslate"], check=True)
try:
import argostranslate
from argostranslate import translate, package
except ImportError:
Utils.cache_set("is_disabel_argostranslate", True)
print(
"argostranslate not found and install failed , will disable it")
return None
packages = package.get_installed_packages()
installed_packages = {}
for p in packages:
installed_packages[f"{p.from_code}_{p.to_code}"] = p
argosmodel_dir = os.path.join(
Utils.get_models_path(), "argosmodel")
if not os.path.exists(argosmodel_dir):
os.makedirs(argosmodel_dir)
model_name = None
if from_code == "zh" and to_code == "en":
model_name = "zh_en"
elif from_code == "en" and to_code == "zh":
model_name = "en_zh"
else:
return None
if Utils.cache_get(f"argostranslate_{model_name}") is not None:
return Utils.cache_get(f"argostranslate_{model_name}")
if installed_packages.get(model_name, None) is None:
if not os.path.exists(os.path.join(argosmodel_dir, f"translate-{model_name}-1_9.argosmodel")):
argosmodel_file = Utils.download_file(
url=f"https://www.modelscope.cn/api/v1/models/wailovet/MinusZoneAIModels/repo?Revision=master&FilePath=argosmodel%2Ftranslate-{model_name}-1_9.argosmodel",
filepath=os.path.join(
argosmodel_dir, f"translate-{model_name}-1_9.argosmodel"),
)
else:
argosmodel_file = os.path.join(
argosmodel_dir, f"translate-{model_name}-1_9.argosmodel")
package.install_from_path(argosmodel_file)
translate_object = translate.get_translation_from_codes(
from_code=from_code, to_code=to_code)
Utils.cache_set(f"argostranslate_{model_name}", translate_object)
return translate_object
except Exception as e:
print(e)
argostranslate.package.update_package_index()
available_packages = argostranslate.package.get_available_packages()
package_to_install = next(
filter(
lambda x: (x.from_code == from_code and x.to_code ==
to_code), available_packages,
)
)
download_path = package_to_install.download()
print("package_to_install.download():", download_path)
argostranslate.package.install_from_path(download_path)
Utils.cache_set("is_disabel_argostranslate", True)
print(
"argostranslate not found and install failed , will disable it")
print(f"get_translate_object error: {e}")
return None
translation = translate.get_translation_from_codes(
from_code, to_code)
if translation is None:
return text
def translate_text(text, from_code, to_code):
translation = Utils.get_translate_object(from_code, to_code)
if translation is None:
return text
# Translate
translatedText = translation.translate(
@@ -677,6 +717,9 @@ class Utils:
def to_debug_prompt(p):
if p is None:
return ""
zh = Utils.en2zh(p)
if p == zh:
return p
zh = Utils.split_en_to_zh(p)
p = p.strip()
return f"""
@@ -766,7 +809,7 @@ class Utils:
cache_value = Utils.get_cache_by_local(cache_key)
if cache_value is not None:
return cache_value
sha256 = Utils.file_hash(file_path, hashlib.sha256)
Utils.set_cache_by_local(cache_key, sha256)
return sha256
+20
View File
@@ -47,3 +47,23 @@ Describe this image in detail please.
The language of reply is English only!!!
Starts with "In the image,"
"""
M_ImageCaptioner2_System = """
You are an assistant who perfectly describes images.
"""
M_ImageCaptioner2_Prompt = """
Describe this image in detail please.
The language of reply is English only!!!
Starts with "In the image,"
"""
ImageCaptionerPostProcessing_System = """
I want you to write me a detailed list of tips for Content.
Write a very short description of the scene and put it in the 'short_describes' field
Write complete [moods, styles, lights, elements, objects] of the word array and put it in the '$_tags' field
Don't include anything that isn't in Content.
The language of reply is English only!!!
"""