From 0c7d132eecef13f11db49e37e2be34bb1f750937 Mon Sep 17 00:00:00 2001 From: root Date: Thu, 19 Feb 2026 12:00:51 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E5=9B=BE=E7=89=87=E4=B8=8A=E4=BC=A0?= =?UTF-8?q?=E6=8B=92=E7=BB=9D=E8=BF=94=E5=9B=9E=E5=8F=8B=E5=A5=BD=E9=94=99?= =?UTF-8?q?=E8=AF=AF=E4=BF=A1=E6=81=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/api/v1/public_api/imagine.py | 25 +++++++++++++++--- app/services/grok/services/image_edit.py | 33 ++++++++++++++++++++++++ 2 files changed, 54 insertions(+), 4 deletions(-) diff --git a/app/api/v1/public_api/imagine.py b/app/api/v1/public_api/imagine.py index ab235a2..1816fb5 100644 --- a/app/api/v1/public_api/imagine.py +++ b/app/api/v1/public_api/imagine.py @@ -16,6 +16,7 @@ from pydantic import BaseModel from app.core.auth import verify_public_key, get_public_api_key, is_public_enabled from app.core.config import get_config +from app.core.exceptions import AppException from app.core.logger import logger from app.api.v1.image import resolve_aspect_ratio from app.services.grok.services.image import ImageGenerationService @@ -913,11 +914,14 @@ async def public_imagine_edit(data: ImagineEditRequest, request: Request): ) raise except Exception as e: + message = str(e) + if not message: + message = "编辑失败,请稍后重试" await queue.put( { "type": "error", "payload": { - "message": str(e), + "message": message, }, } ) @@ -964,7 +968,12 @@ async def public_imagine_edit(data: ImagineEditRequest, request: Request): headers={"Cache-Control": "no-cache", "Connection": "keep-alive"}, ) - return await _run_once(progress_cb=None) + try: + return await _run_once(progress_cb=None) + except AppException as e: + raise HTTPException(status_code=e.status_code, detail=e.message) + except Exception: + raise HTTPException(status_code=500, detail="编辑失败,请稍后重试") class ImagineStopRequest(BaseModel): @@ -1155,11 +1164,14 @@ async def public_imagine_workbench_edit(data: ImagineWorkbenchEditRequest, reque ) raise except Exception as e: + message = str(e) + if not message: + message = "编辑失败,请稍后重试" await queue.put( { "type": "error", "payload": { - "message": str(e), + "message": message, }, } ) @@ -1207,4 +1219,9 @@ async def public_imagine_workbench_edit(data: ImagineWorkbenchEditRequest, reque headers={"Cache-Control": "no-cache", "Connection": "keep-alive"}, ) - return await _run_once(progress_cb=None) + try: + return await _run_once(progress_cb=None) + except AppException as e: + raise HTTPException(status_code=e.status_code, detail=e.message) + except Exception: + raise HTTPException(status_code=500, detail="编辑失败,请稍后重试") diff --git a/app/services/grok/services/image_edit.py b/app/services/grok/services/image_edit.py index 7f77842..ed880e2 100644 --- a/app/services/grok/services/image_edit.py +++ b/app/services/grok/services/image_edit.py @@ -40,6 +40,25 @@ class ImageEditResult: data: Union[AsyncGenerator[str, None], List[str]] +def _is_upload_rejected_error(exc: Exception) -> bool: + """判断是否为上游审核导致的上传拒绝。""" + msg = str(exc or "").lower() + if "content moderated" in msg or "content-moderated" in msg: + return True + if '"code":3' in msg or "'code': 3" in msg: + return True + + details = getattr(exc, "details", None) + if isinstance(details, dict): + body = str(details.get("body") or "").lower() + if "content moderated" in body or "content-moderated" in body: + return True + if '"code":3' in body or "'code': 3" in body: + return True + + return False + + class ImageEditService: """Image edit orchestration service.""" @@ -438,6 +457,20 @@ class ImageEditService: image_urls.append( f"https://assets.grok.com/{file_uri.lstrip('/')}" ) + except Exception as e: + if _is_upload_rejected_error(e): + raise AppException( + message="图片上传被拒绝,请更换图片后重试", + error_type=ErrorType.INVALID_REQUEST.value, + code="upload_rejected", + status_code=400, + ) + raise AppException( + message="图片上传失败,请稍后重试", + error_type=ErrorType.SERVER.value, + code="upload_failed", + status_code=502, + ) finally: await upload_service.close()