修复chat生成参数提交错误BUG|模型引擎积分设置关联开发优化成功|视频/图片生成引擎API开发完成

This commit is contained in:
2026-05-28 13:00:27 +08:00
parent 5021cfd35b
commit edef601f7c
17 changed files with 890 additions and 483 deletions
+34 -2
View File
@@ -651,6 +651,30 @@ async def delete_image_engine(
return {"message": "ok"}
async def _validate_credit_ratio_engine(db: AsyncSession, req: CreditRatioCreate) -> None:
"""校验积分规则绑定的引擎是否存在。
CreditRatio.model_config_id 为兼容旧字段名,当前实际保存引擎ID:
- gen_type=image 时对应 image_engines.id
- gen_type=video 时对应 video_engines.id
"""
gen_type = (req.gen_type or "").lower().strip()
engine_id = (req.model_config_id or "").strip()
if gen_type not in ("image", "video"):
raise HTTPException(status_code=400, detail="gen_type 仅支持 image 或 video")
if not engine_id:
raise HTTPException(status_code=400, detail="model_config_id 不能为空,当前字段用于保存图片/视频引擎ID")
model = ImageEngine if gen_type == "image" else VideoEngine
result = await db.execute(select(model).where(model.id == engine_id).limit(1))
engine = result.scalar_one_or_none()
if not engine:
detail = "图片积分规则绑定的图片引擎不存在" if gen_type == "image" else "视频积分规则绑定的视频引擎不存在"
raise HTTPException(status_code=400, detail=detail)
# ── Credit Ratio ─────────────────────────────────────────
@router.get("/credit-ratios", response_model=list[CreditRatioOut])
@@ -668,7 +692,11 @@ async def create_credit_ratio(
admin: User = Depends(get_admin_user),
db: AsyncSession = Depends(get_db),
):
ratio = CreditRatio(id=generate_id(), **req.model_dump())
await _validate_credit_ratio_engine(db, req)
data = req.model_dump()
data["gen_type"] = data["gen_type"].lower().strip()
data["model_config_id"] = data["model_config_id"].strip()
ratio = CreditRatio(id=generate_id(), **data)
db.add(ratio)
await db.flush()
return ratio
@@ -687,7 +715,11 @@ async def update_credit_ratio(
ratio = result.scalar_one_or_none()
if not ratio:
raise HTTPException(status_code=404, detail="积分比例不存在")
for k, v in req.model_dump().items():
await _validate_credit_ratio_engine(db, req)
data = req.model_dump()
data["gen_type"] = data["gen_type"].lower().strip()
data["model_config_id"] = data["model_config_id"].strip()
for k, v in data.items():
setattr(ratio, k, v)
await db.flush()
return ratio
+66
View File
@@ -6,6 +6,7 @@ from app.dependencies import get_current_user, get_db
from app.models.chat_generation_task import ChatGenerationTask
from app.models.user import User
from app.schemas.generation_ai import (
GenerationAIEngineOptionsOut,
GenerationAIHistoryDayItemsOut,
GenerationAIHistoryGroupedOut,
GenerationAIRetryOut,
@@ -15,6 +16,7 @@ from app.schemas.generation_ai import (
)
from app.services.generation_ai_service import (
create_async_generation_task,
list_generation_ai_engine_options,
list_async_generation_tasks,
list_generation_history_day_items,
list_generation_history_grouped_days,
@@ -29,6 +31,70 @@ router = APIRouter(
)
@router.get(
"/engines",
response_model=GenerationAIEngineOptionsOut,
summary="获取AI图片/视频可用引擎列表",
description=(
"获取当前启用状态的图片生成引擎和视频生成引擎。"
"返回格式为 engine.image 和 engine.video 两个数组。"
"前端创建 /generation-ai/tasks 任务时,可以把对应引擎 id 作为 engine_id 传入。"
"该接口只返回前端需要展示和选择的模型能力信息,不返回 api_key 等敏感配置。"
),
responses={
200: {
"description": "查询成功,返回当前启用的图片/视频生成引擎列表",
"content": {
"application/json": {
"example": {
"engine": {
"image": [
{
"id": "image_engine_xxx",
"name": "豆包文生图",
"provider": "ark",
"model_name": "doubao-seedream-5-0-260128",
"supported_models": ["doubao-seedream-5-0-260128"],
"supported_sizes": {
"2K": {
"1:1": "2048x2048",
"16:9": "2560x1440",
}
},
"default_size": "2K",
"priority": 10,
}
],
"video": [
{
"id": "video_engine_xxx",
"name": "Seedance 2.0",
"provider": "ark",
"model_name": "doubao-seedance-2-0-260128",
"supported_ratios": ["16:9", "4:3", "1:1", "3:4", "9:16", "21:9"],
"supported_resolutions": ["480p", "720p", "1080p"],
"supported_durations": [4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15],
"max_duration": 15,
"priority": 10,
}
],
}
}
}
},
},
401: {
"description": "未登录或 Token 无效",
},
},
)
async def list_engines(
current_user: User = Depends(get_current_user),
db: AsyncSession = Depends(get_db),
):
return await list_generation_ai_engine_options(db)
@router.post(
"/tasks",
response_model=GenerationAITaskOut,