|
|
@@ -159,6 +159,8 @@ class ModelHandler:
|
|
|
model = self._get_gemini_model()
|
|
|
elif model_type == "qwen":
|
|
|
model = self._get_qwen_model()
|
|
|
+ elif model_type == "qwen3_30b":
|
|
|
+ model = self._get_qwen3_30b_model()
|
|
|
elif model_type == "deepseek":
|
|
|
model = self._get_deepseek_model()
|
|
|
elif model_type == "lq_qwen3_8b":
|
|
|
@@ -199,6 +201,87 @@ class ModelHandler:
|
|
|
# 如果所有模型都失败,抛出异常
|
|
|
raise ModelConnectionError(f"无法初始化任何模型服务: {e}")
|
|
|
|
|
|
+ def get_model_by_name(self, model_type: str = None):
|
|
|
+ """
|
|
|
+ 根据模型名称动态获取指定的AI模型实例
|
|
|
+
|
|
|
+ Args:
|
|
|
+ model_type: 模型类型名称,如果为None则使用配置文件中的默认模型
|
|
|
+ 支持的模型类型:doubao, qwen, qwen3_30b, deepseek, gemini,
|
|
|
+ lq_qwen3_8b, lq_qwen3_8b_lq_lora,
|
|
|
+ lq_qwen3_4b, qwen_local_14b
|
|
|
+
|
|
|
+ Returns:
|
|
|
+ ChatOpenAI: 配置好的AI模型实例
|
|
|
+
|
|
|
+ Note:
|
|
|
+ 该方法支持动态切换模型,不受配置文件中的默认MODEL_TYPE限制
|
|
|
+ 如果model_type为None,则使用配置文件中的默认模型
|
|
|
+ 如果model_type无效,则使用gemini作为降级模型
|
|
|
+ """
|
|
|
+ # 如果未指定模型类型,使用配置文件中的默认模型
|
|
|
+ if model_type is None:
|
|
|
+ model_type = self.config.get("model", "MODEL_TYPE")
|
|
|
+
|
|
|
+ logger.info(f"动态获取AI模型,模型类型: {model_type}")
|
|
|
+
|
|
|
+ # 检查缓存
|
|
|
+ cache_key = f"chat_{model_type}"
|
|
|
+ if cache_key in self._model_cache:
|
|
|
+ logger.info(f"使用缓存的模型: {model_type}")
|
|
|
+ return self._model_cache[cache_key]
|
|
|
+
|
|
|
+ model = None
|
|
|
+
|
|
|
+ try:
|
|
|
+ if model_type == "doubao":
|
|
|
+ model = self._get_doubao_model()
|
|
|
+ elif model_type == "gemini":
|
|
|
+ model = self._get_gemini_model()
|
|
|
+ elif model_type == "qwen":
|
|
|
+ model = self._get_qwen_model()
|
|
|
+ elif model_type == "qwen3_30b":
|
|
|
+ model = self._get_qwen3_30b_model()
|
|
|
+ elif model_type == "deepseek":
|
|
|
+ model = self._get_deepseek_model()
|
|
|
+ elif model_type == "lq_qwen3_8b":
|
|
|
+ model = self._get_lq_qwen3_8b_model()
|
|
|
+ elif model_type == "lq_qwen3_8b_lq_lora":
|
|
|
+ model = self._get_lq_qwen3_8b_lora_model()
|
|
|
+ elif model_type == "lq_qwen3_4b":
|
|
|
+ model = self._get_lq_qwen3_4b_model()
|
|
|
+ elif model_type == "qwen_local_14b":
|
|
|
+ model = self._get_qwen_local_14b_model()
|
|
|
+ else:
|
|
|
+ # 默认返回gemini
|
|
|
+ logger.warning(f"未知的模型类型 '{model_type}',使用默认gemini模型")
|
|
|
+ model = self._get_gemini_model()
|
|
|
+
|
|
|
+ if model:
|
|
|
+ self._model_cache[cache_key] = model
|
|
|
+ logger.info(f"AI模型动态初始化完成: {model_type}")
|
|
|
+ return model
|
|
|
+ else:
|
|
|
+ raise ModelAPIError(f"模型初始化返回None: {model_type}")
|
|
|
+
|
|
|
+ except Exception as e:
|
|
|
+ logger.error(f"动态获取模型失败 [{model_type}]: {e}")
|
|
|
+
|
|
|
+ # 尝试使用gemini作为降级方案
|
|
|
+ if model_type != "gemini":
|
|
|
+ logger.info("尝试使用Gemini模型作为降级方案")
|
|
|
+ try:
|
|
|
+ fallback_model = self._get_gemini_model()
|
|
|
+ if fallback_model:
|
|
|
+ self._model_cache[cache_key] = fallback_model
|
|
|
+ logger.warning(f"已切换到Gemini降级模型")
|
|
|
+ return fallback_model
|
|
|
+ except Exception as fallback_error:
|
|
|
+ logger.error(f"降级模型也失败: {fallback_error}")
|
|
|
+
|
|
|
+ # 如果所有模型都失败,抛出异常
|
|
|
+ raise ModelConnectionError(f"无法初始化任何模型服务: {e}")
|
|
|
+
|
|
|
def get_embedding_model(self):
|
|
|
"""
|
|
|
获取Embedding模型实例
|
|
|
@@ -341,6 +424,55 @@ class ModelHandler:
|
|
|
error = ModelAPIError(f"通义千问模型初始化异常: {e}")
|
|
|
return self._handle_model_error("qwen", error)
|
|
|
|
|
|
+ def _get_qwen3_30b_model(self):
|
|
|
+ """
|
|
|
+ 获取Qwen3-30B模型
|
|
|
+
|
|
|
+ Returns:
|
|
|
+ ChatOpenAI: 配置好的Qwen3-30B模型实例
|
|
|
+ """
|
|
|
+ try:
|
|
|
+ qwen3_30b_url = self.config.get("qwen3_30b", "QWEN3_30B_SERVER_URL")
|
|
|
+ qwen3_30b_model_id = self.config.get("qwen3_30b", "QWEN3_30B_MODEL_ID")
|
|
|
+ qwen3_30b_api_key = self.config.get("qwen3_30b", "QWEN3_30B_API_KEY")
|
|
|
+
|
|
|
+ # 验证配置完整性
|
|
|
+ if not all([qwen3_30b_url, qwen3_30b_model_id, qwen3_30b_api_key]):
|
|
|
+ missing = []
|
|
|
+ if not qwen3_30b_url:
|
|
|
+ missing.append("QWEN3_30B_SERVER_URL")
|
|
|
+ if not qwen3_30b_model_id:
|
|
|
+ missing.append("QWEN3_30B_MODEL_ID")
|
|
|
+ if not qwen3_30b_api_key:
|
|
|
+ missing.append("QWEN3_30B_API_KEY")
|
|
|
+ raise ModelConfigError(f"Qwen3-30B模型配置不完整,缺少: {', '.join(missing)}")
|
|
|
+
|
|
|
+ # 检查连接
|
|
|
+ if not self._check_connection(qwen3_30b_url, qwen3_30b_api_key):
|
|
|
+ logger.warning(f"Qwen3-30B模型服务连接失败: {qwen3_30b_url}")
|
|
|
+ raise ModelConnectionError(f"无法连接到Qwen3-30B模型服务: {qwen3_30b_url}")
|
|
|
+
|
|
|
+ llm = ChatOpenAI(
|
|
|
+ base_url=qwen3_30b_url,
|
|
|
+ model=qwen3_30b_model_id,
|
|
|
+ api_key=qwen3_30b_api_key,
|
|
|
+ temperature=0.7,
|
|
|
+ timeout=self.REQUEST_TIMEOUT,
|
|
|
+ extra_body={
|
|
|
+ "enable_thinking": False,
|
|
|
+ })
|
|
|
+
|
|
|
+ logger.info(f"Qwen3-30B模型初始化成功: {qwen3_30b_model_id}")
|
|
|
+ return llm
|
|
|
+
|
|
|
+ except ModelConfigError:
|
|
|
+ raise
|
|
|
+ except ModelConnectionError:
|
|
|
+ raise
|
|
|
+ except Exception as e:
|
|
|
+ error = ModelAPIError(f"Qwen3-30B模型初始化异常: {e}")
|
|
|
+ return self._handle_model_error("qwen3_30b", error)
|
|
|
+
|
|
|
def _get_deepseek_model(self):
|
|
|
"""
|
|
|
获取DeepSeek模型
|