48 lines
1.8 KiB
Python
48 lines
1.8 KiB
Python
# -*- coding: utf-8 -*-
|
||
"""
|
||
图片预检 - 下载后检查尺寸/格式/是否损坏,不合格直接拒单
|
||
"""
|
||
import os
|
||
import logging
|
||
from typing import Tuple
|
||
|
||
logger = logging.getLogger(__name__)
|
||
|
||
# 可配置
|
||
MIN_WIDTH = int(os.getenv("IMAGE_PRECHECK_MIN_WIDTH", "50"))
|
||
MIN_HEIGHT = int(os.getenv("IMAGE_PRECHECK_MIN_HEIGHT", "50"))
|
||
MAX_WIDTH = int(os.getenv("IMAGE_PRECHECK_MAX_WIDTH", "8000"))
|
||
MAX_HEIGHT = int(os.getenv("IMAGE_PRECHECK_MAX_HEIGHT", "8000"))
|
||
MIN_SIZE = int(os.getenv("IMAGE_PRECHECK_MIN_BYTES", "100")) # 至少 100 字节
|
||
MAX_SIZE = int(os.getenv("IMAGE_PRECHECK_MAX_BYTES", "0")) # 0=不限制
|
||
SUPPORTED_FORMATS = (".jpg", ".jpeg", ".png", ".gif", ".webp", ".bmp")
|
||
|
||
|
||
def precheck(local_path: str) -> Tuple[bool, str]:
|
||
"""
|
||
预检图片文件。
|
||
|
||
Returns:
|
||
(ok, message) - ok=False 时 message 为拒单原因
|
||
"""
|
||
if not os.path.exists(local_path):
|
||
return False, "图片文件不存在"
|
||
size = os.path.getsize(local_path)
|
||
if size < MIN_SIZE:
|
||
return False, f"图片太小({size} 字节),可能损坏或格式异常"
|
||
if MAX_SIZE > 0 and size > MAX_SIZE:
|
||
return False, f"图片过大({size/1024/1024:.1f}MB),超过 {MAX_SIZE/1024/1024:.0f}MB 限制"
|
||
|
||
try:
|
||
from PIL import Image
|
||
with Image.open(local_path) as img:
|
||
w, h = img.size
|
||
if w < MIN_WIDTH or h < MIN_HEIGHT:
|
||
return False, f"图片尺寸过小({w}x{h}),最小 {MIN_WIDTH}x{MIN_HEIGHT}"
|
||
if w > MAX_WIDTH or h > MAX_HEIGHT:
|
||
return False, f"图片尺寸过大({w}x{h}),最大 {MAX_WIDTH}x{MAX_HEIGHT}"
|
||
img.verify()
|
||
except Exception as e:
|
||
return False, f"图片无法读取或已损坏:{str(e)[:50]}"
|
||
return True, ""
|