From 29427a0ad695fdf7f7156809f5da112a87d980d4 Mon Sep 17 00:00:00 2001 From: shaohuzhang1 <80892890+shaohuzhang1@users.noreply.github.com> Date: Sun, 28 Apr 2024 11:59:19 +0800 Subject: [PATCH 1/6] =?UTF-8?q?fix:=20=E7=A7=81=E6=9C=89=E9=83=A8=E7=BD=B2?= =?UTF-8?q?=E8=AE=A1=E7=AE=97tokens=E6=8A=A5=E9=94=99=20(#284)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/common/config/tokenizer_manage_config.py | 24 +++++++++++++++++++ .../azure_model_provider.py | 5 ++-- .../model/azure_chat_model.py | 24 +++++++++++++++++++ .../model/kimi_chat_model.py | 14 +---------- .../model/ollama_chat_model.py | 14 +---------- .../model/openai_chat_model.py | 14 +---------- .../model/qwen_chat_model.py | 24 +++++++++++++++++++ .../qwen_model_provider.py | 3 ++- .../model/qian_fan_chat_model.py | 14 +---------- .../xf_model_provider/model/xf_chat_model.py | 12 +++++++++- .../model/zhipu_chat_model.py | 24 +++++++++++++++++++ .../zhipu_model_provider.py | 3 ++- 12 files changed, 118 insertions(+), 57 deletions(-) create mode 100644 apps/common/config/tokenizer_manage_config.py create mode 100644 apps/setting/models_provider/impl/azure_model_provider/model/azure_chat_model.py create mode 100644 apps/setting/models_provider/impl/qwen_model_provider/model/qwen_chat_model.py create mode 100644 apps/setting/models_provider/impl/zhipu_model_provider/model/zhipu_chat_model.py diff --git a/apps/common/config/tokenizer_manage_config.py b/apps/common/config/tokenizer_manage_config.py new file mode 100644 index 000000000..1d3fa8dd9 --- /dev/null +++ b/apps/common/config/tokenizer_manage_config.py @@ -0,0 +1,24 @@ +# coding=utf-8 +""" + @project: maxkb + @Author:虎 + @file: tokenizer_manage_config.py + @date:2024/4/28 10:17 + @desc: +""" + + +class TokenizerManage: + tokenizer = None + + @staticmethod + def get_tokenizer(): + from transformers import GPT2TokenizerFast + if TokenizerManage.tokenizer is None: + TokenizerManage.tokenizer = GPT2TokenizerFast.from_pretrained( + 'gpt2', + cache_dir="/opt/maxkb/model/tokenizer", + local_files_only=True, + resume_download=False, + force_download=False) + return TokenizerManage.tokenizer diff --git a/apps/setting/models_provider/impl/azure_model_provider/azure_model_provider.py b/apps/setting/models_provider/impl/azure_model_provider/azure_model_provider.py index f58f8744c..1f04a268a 100644 --- a/apps/setting/models_provider/impl/azure_model_provider/azure_model_provider.py +++ b/apps/setting/models_provider/impl/azure_model_provider/azure_model_provider.py @@ -19,6 +19,7 @@ from common.util.file_util import get_file_content from setting.models_provider.base_model_provider import IModelProvider, ModelProvideInfo, BaseModelCredential, \ ModelInfo, \ ModelTypeConst, ValidCode +from setting.models_provider.impl.azure_model_provider.model.azure_chat_model import AzureChatModel from smartdoc.conf import PROJECT_DIR @@ -119,8 +120,8 @@ class AzureModelProvider(IModelProvider): def get_model(self, model_type, model_name, model_credential: Dict[str, object], **model_kwargs) -> AzureChatOpenAI: model_info: ModelInfo = model_dict.get(model_name) - azure_chat_open_ai = AzureChatOpenAI( - openai_api_base=model_credential.get('api_base'), + azure_chat_open_ai = AzureChatModel( + azure_endpoint=model_credential.get('api_base'), openai_api_version=model_info.api_version if model_name in model_dict else model_credential.get( 'api_version'), deployment_name=model_credential.get('deployment_name'), diff --git a/apps/setting/models_provider/impl/azure_model_provider/model/azure_chat_model.py b/apps/setting/models_provider/impl/azure_model_provider/model/azure_chat_model.py new file mode 100644 index 000000000..f11249de0 --- /dev/null +++ b/apps/setting/models_provider/impl/azure_model_provider/model/azure_chat_model.py @@ -0,0 +1,24 @@ +# coding=utf-8 +""" + @project: maxkb + @Author:虎 + @file: azure_chat_model.py + @date:2024/4/28 11:45 + @desc: +""" +from typing import List + +from langchain_core.messages import BaseMessage, get_buffer_string +from langchain_openai import AzureChatOpenAI + +from common.config.tokenizer_manage_config import TokenizerManage + + +class AzureChatModel(AzureChatOpenAI): + def get_num_tokens_from_messages(self, messages: List[BaseMessage]) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return sum([len(tokenizer.encode(get_buffer_string([m]))) for m in messages]) + + def get_num_tokens(self, text: str) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return len(tokenizer.encode(text)) diff --git a/apps/setting/models_provider/impl/kimi_model_provider/model/kimi_chat_model.py b/apps/setting/models_provider/impl/kimi_model_provider/model/kimi_chat_model.py index c69cae48d..deee11a02 100644 --- a/apps/setting/models_provider/impl/kimi_model_provider/model/kimi_chat_model.py +++ b/apps/setting/models_provider/impl/kimi_model_provider/model/kimi_chat_model.py @@ -11,19 +11,7 @@ from typing import List from langchain_community.chat_models import ChatOpenAI from langchain_core.messages import BaseMessage, get_buffer_string - -class TokenizerManage: - tokenizer = None - - @staticmethod - def get_tokenizer(): - from transformers import GPT2TokenizerFast - if TokenizerManage.tokenizer is None: - TokenizerManage.tokenizer = GPT2TokenizerFast.from_pretrained('gpt2', - cache_dir="/opt/maxkb/model/tokenizer", - resume_download=False, - force_download=False) - return TokenizerManage.tokenizer +from common.config.tokenizer_manage_config import TokenizerManage class KimiChatModel(ChatOpenAI): diff --git a/apps/setting/models_provider/impl/ollama_model_provider/model/ollama_chat_model.py b/apps/setting/models_provider/impl/ollama_model_provider/model/ollama_chat_model.py index 876e1f28d..86c5219d4 100644 --- a/apps/setting/models_provider/impl/ollama_model_provider/model/ollama_chat_model.py +++ b/apps/setting/models_provider/impl/ollama_model_provider/model/ollama_chat_model.py @@ -11,19 +11,7 @@ from typing import List from langchain_community.chat_models import ChatOpenAI from langchain_core.messages import BaseMessage, get_buffer_string - -class TokenizerManage: - tokenizer = None - - @staticmethod - def get_tokenizer(): - from transformers import GPT2TokenizerFast - if TokenizerManage.tokenizer is None: - TokenizerManage.tokenizer = GPT2TokenizerFast.from_pretrained('gpt2', - cache_dir="/opt/maxkb/model/tokenizer", - resume_download=False, - force_download=False) - return TokenizerManage.tokenizer +from common.config.tokenizer_manage_config import TokenizerManage class OllamaChatModel(ChatOpenAI): diff --git a/apps/setting/models_provider/impl/openai_model_provider/model/openai_chat_model.py b/apps/setting/models_provider/impl/openai_model_provider/model/openai_chat_model.py index 1cdfa2aff..7271fe8ad 100644 --- a/apps/setting/models_provider/impl/openai_model_provider/model/openai_chat_model.py +++ b/apps/setting/models_provider/impl/openai_model_provider/model/openai_chat_model.py @@ -11,19 +11,7 @@ from typing import List from langchain_core.messages import BaseMessage, get_buffer_string from langchain_openai import ChatOpenAI - -class TokenizerManage: - tokenizer = None - - @staticmethod - def get_tokenizer(): - from transformers import GPT2TokenizerFast - if TokenizerManage.tokenizer is None: - TokenizerManage.tokenizer = GPT2TokenizerFast.from_pretrained('gpt2', - cache_dir="/opt/maxkb/model/tokenizer", - resume_download=False, - force_download=False) - return TokenizerManage.tokenizer +from common.config.tokenizer_manage_config import TokenizerManage class OpenAIChatModel(ChatOpenAI): diff --git a/apps/setting/models_provider/impl/qwen_model_provider/model/qwen_chat_model.py b/apps/setting/models_provider/impl/qwen_model_provider/model/qwen_chat_model.py new file mode 100644 index 000000000..d3894d1d0 --- /dev/null +++ b/apps/setting/models_provider/impl/qwen_model_provider/model/qwen_chat_model.py @@ -0,0 +1,24 @@ +# coding=utf-8 +""" + @project: maxkb + @Author:虎 + @file: qwen_chat_model.py + @date:2024/4/28 11:44 + @desc: +""" +from typing import List + +from langchain_community.chat_models import ChatTongyi +from langchain_core.messages import BaseMessage, get_buffer_string + +from common.config.tokenizer_manage_config import TokenizerManage + + +class QwenChatModel(ChatTongyi): + def get_num_tokens_from_messages(self, messages: List[BaseMessage]) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return sum([len(tokenizer.encode(get_buffer_string([m]))) for m in messages]) + + def get_num_tokens(self, text: str) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return len(tokenizer.encode(text)) diff --git a/apps/setting/models_provider/impl/qwen_model_provider/qwen_model_provider.py b/apps/setting/models_provider/impl/qwen_model_provider/qwen_model_provider.py index 46ad1c6ec..179f90368 100644 --- a/apps/setting/models_provider/impl/qwen_model_provider/qwen_model_provider.py +++ b/apps/setting/models_provider/impl/qwen_model_provider/qwen_model_provider.py @@ -18,6 +18,7 @@ from common.forms import BaseForm from common.util.file_util import get_file_content from setting.models_provider.base_model_provider import ModelProvideInfo, ModelTypeConst, BaseModelCredential, \ ModelInfo, IModelProvider, ValidCode +from setting.models_provider.impl.qwen_model_provider.model.qwen_chat_model import QwenChatModel from smartdoc.conf import PROJECT_DIR @@ -66,7 +67,7 @@ class QwenModelProvider(IModelProvider): return 3 def get_model(self, model_type, model_name, model_credential: Dict[str, object], **model_kwargs) -> ChatTongyi: - chat_tong_yi = ChatTongyi( + chat_tong_yi = QwenChatModel( model_name=model_name, dashscope_api_key=model_credential.get('api_key') ) diff --git a/apps/setting/models_provider/impl/wenxin_model_provider/model/qian_fan_chat_model.py b/apps/setting/models_provider/impl/wenxin_model_provider/model/qian_fan_chat_model.py index a2065186e..b07e8a01b 100644 --- a/apps/setting/models_provider/impl/wenxin_model_provider/model/qian_fan_chat_model.py +++ b/apps/setting/models_provider/impl/wenxin_model_provider/model/qian_fan_chat_model.py @@ -18,19 +18,7 @@ from langchain.schema.output import ChatGenerationChunk from langchain.schema.runnable import RunnableConfig from langchain_community.chat_models import QianfanChatEndpoint - -class TokenizerManage: - tokenizer = None - - @staticmethod - def get_tokenizer(): - from transformers import GPT2TokenizerFast - if TokenizerManage.tokenizer is None: - TokenizerManage.tokenizer = GPT2TokenizerFast.from_pretrained('gpt2', - cache_dir="/opt/maxkb/model/tokenizer", - resume_download=False, - force_download=False) - return TokenizerManage.tokenizer +from common.config.tokenizer_manage_config import TokenizerManage class QianfanChatModel(QianfanChatEndpoint): diff --git a/apps/setting/models_provider/impl/xf_model_provider/model/xf_chat_model.py b/apps/setting/models_provider/impl/xf_model_provider/model/xf_chat_model.py index a09d48092..3b6a22c47 100644 --- a/apps/setting/models_provider/impl/xf_model_provider/model/xf_chat_model.py +++ b/apps/setting/models_provider/impl/xf_model_provider/model/xf_chat_model.py @@ -12,11 +12,21 @@ from typing import List, Optional, Any, Iterator from langchain_community.chat_models import ChatSparkLLM from langchain_community.chat_models.sparkllm import _convert_message_to_dict, _convert_delta_to_message_chunk from langchain_core.callbacks import CallbackManagerForLLMRun -from langchain_core.messages import BaseMessage, AIMessageChunk +from langchain_core.messages import BaseMessage, AIMessageChunk, get_buffer_string from langchain_core.outputs import ChatGenerationChunk +from common.config.tokenizer_manage_config import TokenizerManage + class XFChatSparkLLM(ChatSparkLLM): + def get_num_tokens_from_messages(self, messages: List[BaseMessage]) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return sum([len(tokenizer.encode(get_buffer_string([m]))) for m in messages]) + + def get_num_tokens(self, text: str) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return len(tokenizer.encode(text)) + def _stream( self, messages: List[BaseMessage], diff --git a/apps/setting/models_provider/impl/zhipu_model_provider/model/zhipu_chat_model.py b/apps/setting/models_provider/impl/zhipu_model_provider/model/zhipu_chat_model.py new file mode 100644 index 000000000..ceab8988d --- /dev/null +++ b/apps/setting/models_provider/impl/zhipu_model_provider/model/zhipu_chat_model.py @@ -0,0 +1,24 @@ +# coding=utf-8 +""" + @project: maxkb + @Author:虎 + @file: zhipu_chat_model.py + @date:2024/4/28 11:42 + @desc: +""" +from typing import List + +from langchain_community.chat_models import ChatZhipuAI +from langchain_core.messages import BaseMessage, get_buffer_string + +from common.config.tokenizer_manage_config import TokenizerManage + + +class ZhipuChatModel(ChatZhipuAI): + def get_num_tokens_from_messages(self, messages: List[BaseMessage]) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return sum([len(tokenizer.encode(get_buffer_string([m]))) for m in messages]) + + def get_num_tokens(self, text: str) -> int: + tokenizer = TokenizerManage.get_tokenizer() + return len(tokenizer.encode(text)) diff --git a/apps/setting/models_provider/impl/zhipu_model_provider/zhipu_model_provider.py b/apps/setting/models_provider/impl/zhipu_model_provider/zhipu_model_provider.py index b84bb3d15..ebbb3b469 100644 --- a/apps/setting/models_provider/impl/zhipu_model_provider/zhipu_model_provider.py +++ b/apps/setting/models_provider/impl/zhipu_model_provider/zhipu_model_provider.py @@ -18,6 +18,7 @@ from common.forms import BaseForm from common.util.file_util import get_file_content from setting.models_provider.base_model_provider import ModelProvideInfo, ModelTypeConst, BaseModelCredential, \ ModelInfo, IModelProvider, ValidCode +from setting.models_provider.impl.zhipu_model_provider.model.zhipu_chat_model import ZhipuChatModel from smartdoc.conf import PROJECT_DIR @@ -66,7 +67,7 @@ class ZhiPuModelProvider(IModelProvider): return 3 def get_model(self, model_type, model_name, model_credential: Dict[str, object], **model_kwargs) -> ChatZhipuAI: - zhipuai_chat = ChatZhipuAI( + zhipuai_chat = ZhipuChatModel( temperature=0.5, api_key=model_credential.get('api_key'), model=model_name From db4bcfc5d6aea23e0c28056ebf2ae32295c12bae Mon Sep 17 00:00:00 2001 From: Brian Yang Date: Sun, 28 Apr 2024 11:59:57 +0800 Subject: [PATCH 2/6] =?UTF-8?q?perf:=20=E5=A2=9E=E5=8A=A0=E4=BA=86?= =?UTF-8?q?=E6=9B=B4=E5=A4=9A=E5=B8=B8=E7=94=A8=E7=9A=84OpenAI=E6=A8=A1?= =?UTF-8?q?=E5=9E=8B=E5=8F=8A=E5=85=B6=E6=8F=8F=E8=BF=B0=20&=20=E7=8E=B0?= =?UTF-8?q?=E5=9C=A8=E5=8F=AF=E4=BB=A5=E9=80=9A=E8=BF=87tooltip=E6=AD=A3?= =?UTF-8?q?=E5=B8=B8=E6=98=BE=E7=A4=BAModelInfo=E4=B8=ADdesc=E7=9A=84?= =?UTF-8?q?=E5=86=85=E5=AE=B9=20(#269)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../openai_model_provider.py | 35 ++++++- .../template/component/CreateModelDialog.vue | 96 +++++++------------ ui/src/views/template/component/EditModel.vue | 89 ++++++----------- 3 files changed, 93 insertions(+), 127 deletions(-) diff --git a/apps/setting/models_provider/impl/openai_model_provider/openai_model_provider.py b/apps/setting/models_provider/impl/openai_model_provider/openai_model_provider.py index aab6ac08c..983561b95 100644 --- a/apps/setting/models_provider/impl/openai_model_provider/openai_model_provider.py +++ b/apps/setting/models_provider/impl/openai_model_provider/openai_model_provider.py @@ -57,12 +57,39 @@ class OpenAILLMModelCredential(BaseForm, BaseModelCredential): openai_llm_model_credential = OpenAILLMModelCredential() model_dict = { - 'gpt-3.5-turbo': ModelInfo('gpt-3.5-turbo', '', ModelTypeConst.LLM, openai_llm_model_credential, + 'gpt-3.5-turbo': ModelInfo('gpt-3.5-turbo', '最新的gpt-3.5-turbo,随OpenAI调整而更新', ModelTypeConst.LLM, + openai_llm_model_credential, ), - 'gpt-3.5-turbo-0613': ModelInfo('gpt-3.5-turbo-0613', '', ModelTypeConst.LLM, openai_llm_model_credential, + 'gpt-3.5-turbo-0125': ModelInfo('gpt-3.5-turbo-0125', + '2024年1月25日的gpt-3.5-turbo快照,支持上下文长度16,385 tokens', ModelTypeConst.LLM, + openai_llm_model_credential, + ), + 'gpt-3.5-turbo-1106': ModelInfo('gpt-3.5-turbo-1106', + '2023年11月6日的gpt-3.5-turbo快照,支持上下文长度16,385 tokens', ModelTypeConst.LLM, + openai_llm_model_credential, + ), + 'gpt-3.5-turbo-0613': ModelInfo('gpt-3.5-turbo-0613', + '[Legacy] 2023年6月13日的gpt-3.5-turbo快照,将于2024年6月13日弃用', + ModelTypeConst.LLM, openai_llm_model_credential, + ), + 'gpt-4': ModelInfo('gpt-4', '最新的gpt-4,随OpenAI调整而更新', ModelTypeConst.LLM, openai_llm_model_credential, + ), + 'gpt-4-turbo': ModelInfo('gpt-4-turbo', '最新的gpt-4-turbo,随OpenAI调整而更新', ModelTypeConst.LLM, + openai_llm_model_credential, + ), + 'gpt-4-turbo-preview': ModelInfo('gpt-4-turbo-preview', '最新的gpt-4-turbo-preview,随OpenAI调整而更新', + ModelTypeConst.LLM, openai_llm_model_credential, + ), + 'gpt-4-turbo-2024-04-09': ModelInfo('gpt-4-turbo-2024-04-09', + '2024年4月9日的gpt-4-turbo快照,支持上下文长度128,000 tokens', + ModelTypeConst.LLM, openai_llm_model_credential, + ), + 'gpt-4-0125-preview': ModelInfo('gpt-4-0125-preview', '2024年1月25日的gpt-4-turbo快照,支持上下文长度128,000 tokens', + ModelTypeConst.LLM, openai_llm_model_credential, + ), + 'gpt-4-1106-preview': ModelInfo('gpt-4-1106-preview', '2023年11月6日的gpt-4-turbo快照,支持上下文长度128,000 tokens', + ModelTypeConst.LLM, openai_llm_model_credential, ), - 'gpt-4': ModelInfo('gpt-4', '', ModelTypeConst.LLM, openai_llm_model_credential, - ) } diff --git a/ui/src/views/template/component/CreateModelDialog.vue b/ui/src/views/template/component/CreateModelDialog.vue index 3741c0d48..b62d0a3ff 100644 --- a/ui/src/views/template/component/CreateModelDialog.vue +++ b/ui/src/views/template/component/CreateModelDialog.vue @@ -1,37 +1,18 @@ @@ -204,6 +171,7 @@ const list_base_model = (model_type: any) => { ) } } + const close = () => { base_form_data.value = { name: '', model_type: '', model_name: '' } credential_form_data.value = {} diff --git a/ui/src/views/template/component/EditModel.vue b/ui/src/views/template/component/EditModel.vue index 07b81508d..18503e468 100644 --- a/ui/src/views/template/component/EditModel.vue +++ b/ui/src/views/template/component/EditModel.vue @@ -1,31 +1,16 @@ From 4dd9361a97de0f68367e6731d4d5b7eff695d729 Mon Sep 17 00:00:00 2001 From: JinTao Chen <118103548+tongque0@users.noreply.github.com> Date: Sun, 28 Apr 2024 12:43:16 +0800 Subject: [PATCH 3/6] =?UTF-8?q?feat(i18n):=20=E5=88=9D=E5=A7=8B=E5=8C=96?= =?UTF-8?q?=20vue-i18n=20=E4=BB=A5=E6=94=AF=E6=8C=81=E5=9B=BD=E9=99=85?= =?UTF-8?q?=E5=8C=96=20(#275)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ui/env.d.ts | 1 + ui/package.json | 2 + ui/src/components/icons/index.ts | 19 ++++++ ui/src/layout/components/top-bar/index.vue | 48 ++++++++------ ui/src/locales/index.ts | 66 +++++++++++++++++++ ui/src/locales/lang/en_US/components/index.ts | 4 ++ ui/src/locales/lang/en_US/index.ts | 12 ++++ ui/src/locales/lang/en_US/layout.ts | 7 ++ ui/src/locales/lang/en_US/pages/index.ts | 4 ++ ui/src/locales/lang/zh_CN/components/index.ts | 4 ++ ui/src/locales/lang/zh_CN/index.ts | 12 ++++ ui/src/locales/lang/zh_CN/layout.ts | 7 ++ ui/src/locales/lang/zh_CN/pages/index.ts | 4 ++ ui/src/locales/useLocale.ts | 28 ++++++++ ui/src/main.ts | 3 +- 15 files changed, 199 insertions(+), 22 deletions(-) create mode 100644 ui/src/locales/index.ts create mode 100644 ui/src/locales/lang/en_US/components/index.ts create mode 100644 ui/src/locales/lang/en_US/index.ts create mode 100644 ui/src/locales/lang/en_US/layout.ts create mode 100644 ui/src/locales/lang/en_US/pages/index.ts create mode 100644 ui/src/locales/lang/zh_CN/components/index.ts create mode 100644 ui/src/locales/lang/zh_CN/index.ts create mode 100644 ui/src/locales/lang/zh_CN/layout.ts create mode 100644 ui/src/locales/lang/zh_CN/pages/index.ts create mode 100644 ui/src/locales/useLocale.ts diff --git a/ui/env.d.ts b/ui/env.d.ts index ba311a842..52f545270 100644 --- a/ui/env.d.ts +++ b/ui/env.d.ts @@ -11,3 +11,4 @@ declare module 'katex' interface ImportMeta { readonly env: ImportMetaEnv } +declare type Recordable = Record; diff --git a/ui/package.json b/ui/package.json index c9c61d73c..74b34f093 100644 --- a/ui/package.json +++ b/ui/package.json @@ -14,6 +14,7 @@ }, "dependencies": { "@ctrl/tinycolor": "^4.1.0", + "@vueuse/core": "^10.9.0", "axios": "^0.28.0", "cropperjs": "^1.6.2", "echarts": "^5.5.0", @@ -42,6 +43,7 @@ "screenfull": "^6.0.2", "vue": "^3.3.4", "vue-clipboard3": "^2.0.0", + "vue-i18n": "^9.13.1", "vue-router": "^4.2.4" }, "devDependencies": { diff --git a/ui/src/components/icons/index.ts b/ui/src/components/icons/index.ts index 983ac7de2..ffac3bcdd 100644 --- a/ui/src/components/icons/index.ts +++ b/ui/src/components/icons/index.ts @@ -641,6 +641,25 @@ export const iconMap: any = { ]) } }, + 'app-translate': { + iconReader: () => { + return h('svg', { + xmlns: "http://www.w3.org/2000/svg", + viewBox: "0 0 20 20", + fill: "currentColor", + class: "w-5 h-5" + }, [ + h('path', { + d: "M7.75 2.75a.75.75 0 0 0-1.5 0v1.258a32.987 32.987 0 0 0-3.599.278.75.75 0 1 0 .198 1.487A31.545 31.545 0 0 1 8.7 5.545 19.381 19.381 0 0 1 7 9.56a19.418 19.418 0 0 1-1.002-2.05.75.75 0 0 0-1.384.577 20.935 20.935 0 0 0 1.492 2.91 19.613 19.613 0 0 1-3.828 4.154.75.75 0 1 0 .945 1.164A21.116 21.116 0 0 0 7 12.331c.095.132.192.262.29.391a.75.75 0 0 0 1.194-.91c-.204-.266-.4-.538-.59-.815a20.888 20.888 0 0 0 2.333-5.332c.31.031.618.068.924.108a.75.75 0 0 0 .198-1.487 32.832 32.832 0 0 0-3.599-.278V2.75Z" + }), + h('path', { + "fill-rule": "evenodd", + d: "M13 8a.75.75 0 0 1 .671.415l4.25 8.5a.75.75 0 1 1-1.342.67L15.787 16h-5.573l-.793 1.585a.75.75 0 1 1-1.342-.67l4.25-8.5A.75.75 0 0 1 13 8Zm2.037 6.5L13 10.427 10.964 14.5h4.073Z", + "clip-rule": "evenodd" + }) + ]); + } + }, 'app-user': { iconReader: () => { return h('i', [ diff --git a/ui/src/layout/components/top-bar/index.vue b/ui/src/layout/components/top-bar/index.vue index eff56f8f1..a4fa0fba7 100644 --- a/ui/src/layout/components/top-bar/index.vue +++ b/ui/src/layout/components/top-bar/index.vue @@ -11,30 +11,28 @@
- - + + - - + + - - + + + + + + +
@@ -43,9 +41,15 @@ import TopMenu from './top-menu/index.vue' import Avatar from './avatar/index.vue' import { useRouter } from 'vue-router' +import { langList } from '@/locales/index'; +import { useLocale } from '@/locales/useLocale'; const router = useRouter() const defaultTitle = import.meta.env.VITE_APP_TITLE +const { changeLocale } = useLocale(); +const changeLang = (lang: string) => { + changeLocale(lang); +}; function toUrl(url: string) { window.open(url, '_blank') } @@ -58,6 +62,7 @@ function toUrl(url: string) { .app-title-container { margin-right: 45px; + .app-title-icon { background-image: url('@/assets/logo.png'); background-size: 100% 100%; @@ -69,6 +74,7 @@ function toUrl(url: string) { font-size: 24px; } } + .line { height: 2em; } diff --git a/ui/src/locales/index.ts b/ui/src/locales/index.ts new file mode 100644 index 000000000..51f94c11c --- /dev/null +++ b/ui/src/locales/index.ts @@ -0,0 +1,66 @@ +import { useLocalStorage, usePreferredLanguages } from '@vueuse/core'; +import { computed } from 'vue'; +import { createI18n } from 'vue-i18n'; + +// 导入语言文件 +const langModules = import.meta.glob('./lang/*/index.ts', { eager: true }) as Record Promise<{ default: Object }>>; + +const langModuleMap = new Map(); + +export const langCode: Array = []; + +export const localeConfigKey = 'MaxKB-locale'; + +// 获取浏览器默认语言环境 +const languages = usePreferredLanguages(); + +// 生成语言模块列表 +const generateLangModuleMap = () => { + const fullPaths = Object.keys(langModules); + fullPaths.forEach((fullPath) => { + const k = fullPath.replace('./lang', ''); + const startIndex = 1; + const lastIndex = k.lastIndexOf('/'); + const code = k.substring(startIndex, lastIndex); + langCode.push(code); + langModuleMap.set(code, langModules[fullPath]); + }); +}; + +// 导出 Message +const importMessages = computed(() => { + generateLangModuleMap(); + + const message: Recordable = {}; + langModuleMap.forEach((value: any, key) => { + message[key] = value.default; + }); + return message; +}); + +export const i18n = createI18n({ + legacy: false, + locale: useLocalStorage(localeConfigKey, 'zh_CN').value || languages.value[0] || 'zh_CN', + fallbackLocale: 'zh_CN', + messages: importMessages.value, + globalInjection: true, +}); + +export const langList = computed(() => { + if (langModuleMap.size === 0) generateLangModuleMap(); + + const list:any=[] + langModuleMap.forEach((value: any, key) => { + list.push({ + label: value.default.lang, + value: key, + }); + }); + + return list; +}); + +// @ts-ignore +export const { t } = i18n.global; + +export default i18n; diff --git a/ui/src/locales/lang/en_US/components/index.ts b/ui/src/locales/lang/en_US/components/index.ts new file mode 100644 index 000000000..bd77588db --- /dev/null +++ b/ui/src/locales/lang/en_US/components/index.ts @@ -0,0 +1,4 @@ + +export default { + +}; diff --git a/ui/src/locales/lang/en_US/index.ts b/ui/src/locales/lang/en_US/index.ts new file mode 100644 index 000000000..16bd5f6bb --- /dev/null +++ b/ui/src/locales/lang/en_US/index.ts @@ -0,0 +1,12 @@ +import en from 'element-plus/es/locale/lang/en'; +import components from './components'; +import layout from './layout'; +import pages from './pages'; + +export default { + lang: 'English', + layout, + pages, + components, + en, +}; diff --git a/ui/src/locales/lang/en_US/layout.ts b/ui/src/locales/lang/en_US/layout.ts new file mode 100644 index 000000000..7e1e7f9de --- /dev/null +++ b/ui/src/locales/lang/en_US/layout.ts @@ -0,0 +1,7 @@ +export default { + topbar: { + github:"Github", + handbook:"Handbook", + forum:"Forum" + }, +}; diff --git a/ui/src/locales/lang/en_US/pages/index.ts b/ui/src/locales/lang/en_US/pages/index.ts new file mode 100644 index 000000000..bd77588db --- /dev/null +++ b/ui/src/locales/lang/en_US/pages/index.ts @@ -0,0 +1,4 @@ + +export default { + +}; diff --git a/ui/src/locales/lang/zh_CN/components/index.ts b/ui/src/locales/lang/zh_CN/components/index.ts new file mode 100644 index 000000000..bd77588db --- /dev/null +++ b/ui/src/locales/lang/zh_CN/components/index.ts @@ -0,0 +1,4 @@ + +export default { + +}; diff --git a/ui/src/locales/lang/zh_CN/index.ts b/ui/src/locales/lang/zh_CN/index.ts new file mode 100644 index 000000000..db4da9942 --- /dev/null +++ b/ui/src/locales/lang/zh_CN/index.ts @@ -0,0 +1,12 @@ +import zhCn from 'element-plus/es/locale/lang/zh-cn'; +import components from './components'; +import layout from './layout'; +import pages from './pages'; + +export default { + lang: '简体中文', + layout, + pages, + components, + zhCn, +}; diff --git a/ui/src/locales/lang/zh_CN/layout.ts b/ui/src/locales/lang/zh_CN/layout.ts new file mode 100644 index 000000000..f31efa826 --- /dev/null +++ b/ui/src/locales/lang/zh_CN/layout.ts @@ -0,0 +1,7 @@ +export default { + topbar: { + github:"项目地址", + handbook:"用户手册", + forum:"论坛求助" + }, +}; diff --git a/ui/src/locales/lang/zh_CN/pages/index.ts b/ui/src/locales/lang/zh_CN/pages/index.ts new file mode 100644 index 000000000..bd77588db --- /dev/null +++ b/ui/src/locales/lang/zh_CN/pages/index.ts @@ -0,0 +1,4 @@ + +export default { + +}; diff --git a/ui/src/locales/useLocale.ts b/ui/src/locales/useLocale.ts new file mode 100644 index 000000000..c8021627c --- /dev/null +++ b/ui/src/locales/useLocale.ts @@ -0,0 +1,28 @@ +import { useLocalStorage } from '@vueuse/core'; +import { computed } from 'vue'; +import { useI18n } from 'vue-i18n'; + +import { i18n, langCode, localeConfigKey } from '@/locales/index'; + +export function useLocale() { + const { locale } = useI18n({ useScope: 'global' }); + function changeLocale(lang: string) { + // 如果切换的语言不在对应语言文件里则默认为简体中文 + if (!langCode.includes(lang)) { + lang = 'zh_CN'; + } + + locale.value = lang; + useLocalStorage(localeConfigKey, 'zh_CN').value = lang; + } + + const getComponentsLocale = computed(() => { + return i18n.global.getLocaleMessage(locale.value).componentsLocale; + }); + + return { + changeLocale, + getComponentsLocale, + locale, + }; +} diff --git a/ui/src/main.ts b/ui/src/main.ts index 96affdbd5..a978a7efa 100644 --- a/ui/src/main.ts +++ b/ui/src/main.ts @@ -9,7 +9,7 @@ import directives from '@/directives' import App from './App.vue' import router from '@/router' import Components from '@/components' - +import i18n from './locales'; const app = createApp(App) app.use(store) app.use(directives) @@ -24,5 +24,6 @@ app.use(ElementPlus, { app.use(theme) app.use(router) +app.use(i18n); app.use(Components) app.mount('#app') From 9cb21d7c603b273e7bd3fc0716c6a829a3f721c0 Mon Sep 17 00:00:00 2001 From: shaohuzhang1 <80892890+shaohuzhang1@users.noreply.github.com> Date: Sun, 28 Apr 2024 12:56:46 +0800 Subject: [PATCH 4/6] =?UTF-8?q?perf:=20=E9=9A=90=E8=97=8F=E5=9B=BD?= =?UTF-8?q?=E9=99=85=E5=8C=96=E6=8C=89=E9=92=AE=20(#287)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ui/src/layout/components/top-bar/index.vue | 52 +++++++++++++++------- 1 file changed, 37 insertions(+), 15 deletions(-) diff --git a/ui/src/layout/components/top-bar/index.vue b/ui/src/layout/components/top-bar/index.vue index a4fa0fba7..cc240035e 100644 --- a/ui/src/layout/components/top-bar/index.vue +++ b/ui/src/layout/components/top-bar/index.vue @@ -12,25 +12,47 @@
- + - + - + - + - + @@ -41,15 +63,15 @@ import TopMenu from './top-menu/index.vue' import Avatar from './avatar/index.vue' import { useRouter } from 'vue-router' -import { langList } from '@/locales/index'; -import { useLocale } from '@/locales/useLocale'; +import { langList } from '@/locales/index' +import { useLocale } from '@/locales/useLocale' const router = useRouter() const defaultTitle = import.meta.env.VITE_APP_TITLE -const { changeLocale } = useLocale(); +const { changeLocale } = useLocale() const changeLang = (lang: string) => { - changeLocale(lang); -}; + changeLocale(lang) +} function toUrl(url: string) { window.open(url, '_blank') } From a61d8eb0a16745b8ece9e47ddcae1280118ff618 Mon Sep 17 00:00:00 2001 From: shaohuzhang1 <80892890+shaohuzhang1@users.noreply.github.com> Date: Sun, 28 Apr 2024 13:16:12 +0800 Subject: [PATCH 5/6] =?UTF-8?q?perf:=20=E5=A2=9E=E5=8A=A0ollama=E5=9F=BA?= =?UTF-8?q?=E7=A1=80=E6=A8=A1=E5=9E=8B=E9=80=89=E9=A1=B9=20(#288)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../ollama_model_provider.py | 44 ++++++++++++++++++- 1 file changed, 42 insertions(+), 2 deletions(-) diff --git a/apps/setting/models_provider/impl/ollama_model_provider/ollama_model_provider.py b/apps/setting/models_provider/impl/ollama_model_provider/ollama_model_provider.py index 4bbc2d96b..3827bdc68 100644 --- a/apps/setting/models_provider/impl/ollama_model_provider/ollama_model_provider.py +++ b/apps/setting/models_provider/impl/ollama_model_provider/ollama_model_provider.py @@ -74,9 +74,49 @@ model_dict = { 'llama2-chinese:13b', '由于Llama2本身的中文对齐较弱,我们采用中文指令集,对meta-llama/Llama-2-13b-chat-hf进行LoRA微调,使其具备较强的中文对话能力。', ModelTypeConst.LLM, ollama_llm_model_credential), - 'qwen-14b': ModelInfo( + 'llama3:8b': ModelInfo( + 'llama3:8b', + 'Meta Llama 3:迄今为止最有能力的公开产品LLM。8亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'llama3:70b': ModelInfo( + 'llama3:70b', + 'Meta Llama 3:迄今为止最有能力的公开产品LLM。70亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:0.5b': ModelInfo( + 'qwen:0.5b', + 'qwen 1.5 0.5b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。0.5亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:1.8b': ModelInfo( + 'qwen:1.8b', + 'qwen 1.5 1.8b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。1.8亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:4b': ModelInfo( + 'qwen:4b', + 'qwen 1.5 4b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。4亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:7b': ModelInfo( + 'qwen:7b', + 'qwen 1.5 7b 相较于以往版本,模型与人类偏好的对齐程度以及多语1言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。7亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:14b': ModelInfo( 'qwen:14b', - 'qwen 1.5 14b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。', + 'qwen 1.5 14b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。14亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:32b': ModelInfo( + 'qwen:32b', + 'qwen 1.5 32b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。32亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:72b': ModelInfo( + 'qwen:72b', + 'qwen 1.5 72b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。72亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'qwen:110b': ModelInfo( + 'qwen:110b', + 'qwen 1.5 110b 相较于以往版本,模型与人类偏好的对齐程度以及多语言处理能力上有显著增强。所有规模的模型都支持32768个tokens的上下文长度。110亿参数。', + ModelTypeConst.LLM, ollama_llm_model_credential), + 'phi3': ModelInfo( + 'phi3', + 'Phi-3 Mini是Microsoft的3.8B参数,轻量级,最先进的开放模型。', ModelTypeConst.LLM, ollama_llm_model_credential), } From d1fe18166a2022cc6389b9a263d144cd41f03b4c Mon Sep 17 00:00:00 2001 From: shaohuzhang1 <80892890+shaohuzhang1@users.noreply.github.com> Date: Sun, 28 Apr 2024 13:30:26 +0800 Subject: [PATCH 6/6] =?UTF-8?q?perf:=20=E4=BC=98=E5=8C=96=E6=A8=A1?= =?UTF-8?q?=E5=9E=8B=E7=AE=A1=E7=90=86=E5=9F=BA=E7=A1=80=E6=A8=A1=E5=9E=8B?= =?UTF-8?q?=E6=8F=90=E7=A4=BA=20(#289)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../template/component/CreateModelDialog.vue | 77 ++++++++++++++----- ui/src/views/template/component/EditModel.vue | 71 ++++++++++++----- 2 files changed, 111 insertions(+), 37 deletions(-) diff --git a/ui/src/views/template/component/CreateModelDialog.vue b/ui/src/views/template/component/CreateModelDialog.vue index b62d0a3ff..525357f8e 100644 --- a/ui/src/views/template/component/CreateModelDialog.vue +++ b/ui/src/views/template/component/CreateModelDialog.vue @@ -1,18 +1,37 @@