model_factory.py 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336
  1. from typing import Optional
  2. from langchain.callbacks.base import Callbacks
  3. from core.model_providers.error import ProviderTokenNotInitError, LLMBadRequestError
  4. from core.model_providers.model_provider_factory import ModelProviderFactory, DEFAULT_MODELS
  5. from core.model_providers.models.base import BaseProviderModel
  6. from core.model_providers.models.embedding.base import BaseEmbedding
  7. from core.model_providers.models.entity.model_params import ModelKwargs, ModelType
  8. from core.model_providers.models.llm.base import BaseLLM
  9. from core.model_providers.models.moderation.base import BaseModeration
  10. from core.model_providers.models.reranking.base import BaseReranking
  11. from core.model_providers.models.speech2text.base import BaseSpeech2Text
  12. from extensions.ext_database import db
  13. from models.provider import TenantDefaultModel
  14. class ModelFactory:
  15. @classmethod
  16. def get_text_generation_model_from_model_config(cls, tenant_id: str,
  17. model_config: dict,
  18. streaming: bool = False,
  19. callbacks: Callbacks = None) -> Optional[BaseLLM]:
  20. provider_name = model_config.get("provider")
  21. model_name = model_config.get("name")
  22. completion_params = model_config.get("completion_params", {})
  23. return cls.get_text_generation_model(
  24. tenant_id=tenant_id,
  25. model_provider_name=provider_name,
  26. model_name=model_name,
  27. model_kwargs=ModelKwargs(
  28. temperature=completion_params.get('temperature', 0),
  29. max_tokens=completion_params.get('max_tokens', 256),
  30. top_p=completion_params.get('top_p', 0),
  31. frequency_penalty=completion_params.get('frequency_penalty', 0.1),
  32. presence_penalty=completion_params.get('presence_penalty', 0.1)
  33. ),
  34. streaming=streaming,
  35. callbacks=callbacks
  36. )
  37. @classmethod
  38. def get_text_generation_model(cls,
  39. tenant_id: str,
  40. model_provider_name: Optional[str] = None,
  41. model_name: Optional[str] = None,
  42. model_kwargs: Optional[ModelKwargs] = None,
  43. streaming: bool = False,
  44. callbacks: Callbacks = None,
  45. deduct_quota: bool = True) -> Optional[BaseLLM]:
  46. """
  47. get text generation model.
  48. :param tenant_id: a string representing the ID of the tenant.
  49. :param model_provider_name:
  50. :param model_name:
  51. :param model_kwargs:
  52. :param streaming:
  53. :param callbacks:
  54. :param deduct_quota:
  55. :return:
  56. """
  57. is_default_model = False
  58. if model_provider_name is None and model_name is None:
  59. default_model = cls.get_default_model(tenant_id, ModelType.TEXT_GENERATION)
  60. if not default_model:
  61. raise LLMBadRequestError(f"Default model is not available. "
  62. f"Please configure a Default System Reasoning Model "
  63. f"in the Settings -> Model Provider.")
  64. model_provider_name = default_model.provider_name
  65. model_name = default_model.model_name
  66. is_default_model = True
  67. # get model provider
  68. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, model_provider_name)
  69. if not model_provider:
  70. raise ProviderTokenNotInitError(f"Model {model_name} provider credentials is not initialized.")
  71. # init text generation model
  72. model_class = model_provider.get_model_class(model_type=ModelType.TEXT_GENERATION)
  73. try:
  74. model_instance = model_class(
  75. model_provider=model_provider,
  76. name=model_name,
  77. model_kwargs=model_kwargs,
  78. streaming=streaming,
  79. callbacks=callbacks
  80. )
  81. except LLMBadRequestError as e:
  82. if is_default_model:
  83. raise LLMBadRequestError(f"Default model {model_name} is not available. "
  84. f"Please check your model provider credentials.")
  85. else:
  86. raise e
  87. if is_default_model or not deduct_quota:
  88. model_instance.deduct_quota = False
  89. return model_instance
  90. @classmethod
  91. def get_embedding_model(cls,
  92. tenant_id: str,
  93. model_provider_name: Optional[str] = None,
  94. model_name: Optional[str] = None) -> Optional[BaseEmbedding]:
  95. """
  96. get embedding model.
  97. :param tenant_id: a string representing the ID of the tenant.
  98. :param model_provider_name:
  99. :param model_name:
  100. :return:
  101. """
  102. if model_provider_name is None and model_name is None:
  103. default_model = cls.get_default_model(tenant_id, ModelType.EMBEDDINGS)
  104. if not default_model:
  105. raise LLMBadRequestError(f"Default model is not available. "
  106. f"Please configure a Default Embedding Model "
  107. f"in the Settings -> Model Provider.")
  108. model_provider_name = default_model.provider_name
  109. model_name = default_model.model_name
  110. # get model provider
  111. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, model_provider_name)
  112. if not model_provider:
  113. raise ProviderTokenNotInitError(f"Model {model_name} provider credentials is not initialized.")
  114. # init embedding model
  115. model_class = model_provider.get_model_class(model_type=ModelType.EMBEDDINGS)
  116. return model_class(
  117. model_provider=model_provider,
  118. name=model_name
  119. )
  120. @classmethod
  121. def get_reranking_model(cls,
  122. tenant_id: str,
  123. model_provider_name: Optional[str] = None,
  124. model_name: Optional[str] = None) -> Optional[BaseReranking]:
  125. """
  126. get reranking model.
  127. :param tenant_id: a string representing the ID of the tenant.
  128. :param model_provider_name:
  129. :param model_name:
  130. :return:
  131. """
  132. if (model_provider_name is None or len(model_provider_name) == 0) and (model_name is None or len(model_name) == 0):
  133. default_model = cls.get_default_model(tenant_id, ModelType.RERANKING)
  134. if not default_model:
  135. raise LLMBadRequestError(f"Default model is not available. "
  136. f"Please configure a Default Reranking Model "
  137. f"in the Settings -> Model Provider.")
  138. model_provider_name = default_model.provider_name
  139. model_name = default_model.model_name
  140. # get model provider
  141. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, model_provider_name)
  142. if not model_provider:
  143. raise ProviderTokenNotInitError(f"Model {model_name} provider credentials is not initialized.")
  144. # init reranking model
  145. model_class = model_provider.get_model_class(model_type=ModelType.RERANKING)
  146. return model_class(
  147. model_provider=model_provider,
  148. name=model_name
  149. )
  150. @classmethod
  151. def get_speech2text_model(cls,
  152. tenant_id: str,
  153. model_provider_name: Optional[str] = None,
  154. model_name: Optional[str] = None) -> Optional[BaseSpeech2Text]:
  155. """
  156. get speech to text model.
  157. :param tenant_id: a string representing the ID of the tenant.
  158. :param model_provider_name:
  159. :param model_name:
  160. :return:
  161. """
  162. if model_provider_name is None and model_name is None:
  163. default_model = cls.get_default_model(tenant_id, ModelType.SPEECH_TO_TEXT)
  164. if not default_model:
  165. raise LLMBadRequestError(f"Default model is not available. "
  166. f"Please configure a Default Speech-to-Text Model "
  167. f"in the Settings -> Model Provider.")
  168. model_provider_name = default_model.provider_name
  169. model_name = default_model.model_name
  170. # get model provider
  171. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, model_provider_name)
  172. if not model_provider:
  173. raise ProviderTokenNotInitError(f"Model {model_name} provider credentials is not initialized.")
  174. # init speech to text model
  175. model_class = model_provider.get_model_class(model_type=ModelType.SPEECH_TO_TEXT)
  176. return model_class(
  177. model_provider=model_provider,
  178. name=model_name
  179. )
  180. @classmethod
  181. def get_moderation_model(cls,
  182. tenant_id: str,
  183. model_provider_name: str,
  184. model_name: str) -> Optional[BaseModeration]:
  185. """
  186. get moderation model.
  187. :param tenant_id: a string representing the ID of the tenant.
  188. :param model_provider_name:
  189. :param model_name:
  190. :return:
  191. """
  192. # get model provider
  193. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, model_provider_name)
  194. if not model_provider:
  195. raise ProviderTokenNotInitError(f"Model {model_name} provider credentials is not initialized.")
  196. # init moderation model
  197. model_class = model_provider.get_model_class(model_type=ModelType.MODERATION)
  198. return model_class(
  199. model_provider=model_provider,
  200. name=model_name
  201. )
  202. @classmethod
  203. def get_default_model(cls, tenant_id: str, model_type: ModelType) -> TenantDefaultModel:
  204. """
  205. get default model of model type.
  206. :param tenant_id:
  207. :param model_type:
  208. :return:
  209. """
  210. # get default model
  211. default_model = db.session.query(TenantDefaultModel) \
  212. .filter(
  213. TenantDefaultModel.tenant_id == tenant_id,
  214. TenantDefaultModel.model_type == model_type.value
  215. ).first()
  216. if not default_model:
  217. model_provider_rules = ModelProviderFactory.get_provider_rules()
  218. for model_provider_name, model_provider_rule in model_provider_rules.items():
  219. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, model_provider_name)
  220. if not model_provider:
  221. continue
  222. model_list = model_provider.get_supported_model_list(model_type)
  223. if model_list:
  224. model_info = model_list[0]
  225. default_model = TenantDefaultModel(
  226. tenant_id=tenant_id,
  227. model_type=model_type.value,
  228. provider_name=model_provider_name,
  229. model_name=model_info['id']
  230. )
  231. db.session.add(default_model)
  232. db.session.commit()
  233. break
  234. return default_model
  235. @classmethod
  236. def update_default_model(cls,
  237. tenant_id: str,
  238. model_type: ModelType,
  239. provider_name: str,
  240. model_name: str) -> TenantDefaultModel:
  241. """
  242. update default model of model type.
  243. :param tenant_id:
  244. :param model_type:
  245. :param provider_name:
  246. :param model_name:
  247. :return:
  248. """
  249. model_provider_name = ModelProviderFactory.get_provider_names()
  250. if provider_name not in model_provider_name:
  251. raise ValueError(f'Invalid provider name: {provider_name}')
  252. model_provider = ModelProviderFactory.get_preferred_model_provider(tenant_id, provider_name)
  253. if not model_provider:
  254. raise ProviderTokenNotInitError(f"Model {model_name} provider credentials is not initialized.")
  255. model_list = model_provider.get_supported_model_list(model_type)
  256. model_ids = [model['id'] for model in model_list]
  257. if model_name not in model_ids:
  258. raise ValueError(f'Invalid model name: {model_name}')
  259. # get default model
  260. default_model = db.session.query(TenantDefaultModel) \
  261. .filter(
  262. TenantDefaultModel.tenant_id == tenant_id,
  263. TenantDefaultModel.model_type == model_type.value
  264. ).first()
  265. if default_model:
  266. # update default model
  267. default_model.provider_name = provider_name
  268. default_model.model_name = model_name
  269. db.session.commit()
  270. else:
  271. # create default model
  272. default_model = TenantDefaultModel(
  273. tenant_id=tenant_id,
  274. model_type=model_type.value,
  275. provider_name=provider_name,
  276. model_name=model_name,
  277. )
  278. db.session.add(default_model)
  279. db.session.commit()
  280. return default_model