feat(exam_pkg): 优化出题系统稳定性与推理模型适配

- core/llm_utils: MiMo模型自动注入thinking=disabled参数,全局生效
- config: 新增LLM_DISABLE_THINKING配置项(默认true)
- generator: 推理模型自适应max_tokens(1.5x)、429限流重试+指数退避、v2管线补题机制
- generator: analyze_document_for_exam新增max_total参数控制AI出题上限
- generator: validate_questions_schema兼容type和question_type字段
- grader: 主观题max_tokens从1000提升至2000、fuzzy_match增加编辑距离容错
- manager: results变量初始化防NameError、透传max_total参数
- api: /exam/generate-smart支持max_total请求参数
This commit is contained in:
lacerate551
2026-06-22 18:51:11 +08:00
parent b966be5417
commit a31ee4bba0
8 changed files with 475 additions and 75 deletions

View File

@@ -11,6 +11,24 @@ from typing import List, Optional, Union, Iterator, Callable
logger = logging.getLogger(__name__)
# MiMo 推理模型关键词(用于识别需要 thinking 参数的模型)
_MIMO_MODEL_KEYWORDS = ('mimo',)
def _is_mimo_model(model_name: str) -> bool:
"""判断是否为小米 MiMo 模型(支持 thinking 参数)"""
if not model_name:
return False
return any(kw in model_name.lower() for kw in _MIMO_MODEL_KEYWORDS)
def _inject_mimo_thinking(kwargs: dict, model: str, disable_thinking: bool = True) -> dict:
"""为 MiMo 模型注入 thinking 参数。返回更新后的 kwargs。"""
if not _is_mimo_model(model):
return kwargs
extra = dict(kwargs.get('extra_body') or {})
extra['thinking'] = {'type': 'disabled' if disable_thinking else 'enabled'}
kwargs['extra_body'] = extra
return kwargs
def call_llm(
client,
@@ -57,6 +75,13 @@ def call_llm(
if messages is None:
messages = [{"role": "user", "content": prompt}]
# MiMo 模型自动注入 thinking 参数
try:
from config import LLM_DISABLE_THINKING
except ImportError:
LLM_DISABLE_THINKING = True
kwargs = _inject_mimo_thinking(kwargs, model, disable_thinking=LLM_DISABLE_THINKING)
try:
response = client.chat.completions.create(
model=model,
@@ -145,6 +170,13 @@ def call_llm_stream(
if messages is None:
messages = [{"role": "user", "content": prompt}]
# MiMo 模型自动注入 thinking 参数
try:
from config import LLM_DISABLE_THINKING
except ImportError:
LLM_DISABLE_THINKING = True
kwargs = _inject_mimo_thinking(kwargs, model, disable_thinking=LLM_DISABLE_THINKING)
try:
stream = client.chat.completions.create(
model=model,