You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

143 lines
4.5 KiB
Python

# -*- coding: utf-8 -*-
"""
响应数据模型
定义 API 响应的数据结构
"""
from typing import Any, Dict, List, Optional
from pydantic import BaseModel, Field
class ErrorDetail(BaseModel):
"""错误详情"""
code: str = Field(..., description="错误代码")
message: str = Field(..., description="错误信息")
details: Optional[Dict[str, Any]] = Field(
default=None,
description="额外的错误详情",
)
class TextBlockData(BaseModel):
"""文本块数据"""
text: str = Field(..., description="识别出的文本内容")
confidence: float = Field(..., description="置信度 (0.0 ~ 1.0)")
bbox: List[List[float]] = Field(
...,
description="边界框 4 个顶点坐标 [[x1,y1], [x2,y2], [x3,y3], [x4,y4]]",
)
bbox_with_offset: List[List[float]] = Field(
...,
description="带偏移的边界框坐标 (已还原到原图坐标系)",
)
center: List[float] = Field(..., description="文本块中心点坐标 [x, y]")
width: float = Field(..., description="文本块宽度 (像素)")
height: float = Field(..., description="文本块高度 (像素)")
class OCRResultData(BaseModel):
"""OCR 识别结果数据"""
processing_time_ms: float = Field(..., description="处理耗时 (毫秒)")
text_count: int = Field(..., description="识别出的文本块数量")
average_confidence: float = Field(
...,
description="所有文本块的平均置信度",
)
roi_applied: bool = Field(..., description="是否应用了 ROI 裁剪")
roi_rect: Optional[List[int]] = Field(
default=None,
description="ROI 矩形区域 [x, y, width, height]",
)
text_blocks: List[TextBlockData] = Field(
default_factory=list,
description="识别出的文本块列表",
)
annotated_image_base64: Optional[str] = Field(
default=None,
description="标注后的图片 (Base64 编码)",
)
class OCRResponse(BaseModel):
"""OCR 识别响应"""
success: bool = Field(..., description="请求是否成功")
data: Optional[OCRResultData] = Field(
default=None,
description="识别结果数据",
)
error: Optional[ErrorDetail] = Field(
default=None,
description="错误信息 (仅在失败时存在)",
)
class ExpressPersonData(BaseModel):
"""快递单人员信息"""
name: Optional[str] = Field(default=None, description="姓名")
phone: Optional[str] = Field(default=None, description="电话")
address: Optional[str] = Field(default=None, description="地址")
class ExpressInfoData(BaseModel):
"""快递单结构化信息"""
tracking_number: Optional[str] = Field(default=None, description="运单号")
sender: ExpressPersonData = Field(
default_factory=ExpressPersonData,
description="寄件人信息",
)
receiver: ExpressPersonData = Field(
default_factory=ExpressPersonData,
description="收件人信息",
)
courier_company: Optional[str] = Field(
default=None,
description="快递公司名称",
)
confidence: float = Field(default=0.0, description="平均置信度")
extra_fields: Dict[str, str] = Field(
default_factory=dict,
description="其他识别到的额外字段",
)
raw_text: str = Field(default="", description="原始合并文本")
class ExpressResultData(BaseModel):
"""快递单解析结果数据"""
processing_time_ms: float = Field(..., description="处理耗时 (毫秒)")
express_info: ExpressInfoData = Field(..., description="快递单结构化信息")
merged_text: str = Field(..., description="智能合并后的完整文本")
annotated_image_base64: Optional[str] = Field(
default=None,
description="标注后的图片 (Base64 编码)",
)
class ExpressResponse(BaseModel):
"""快递单解析响应"""
success: bool = Field(..., description="请求是否成功")
data: Optional[ExpressResultData] = Field(
default=None,
description="解析结果数据",
)
error: Optional[ErrorDetail] = Field(
default=None,
description="错误信息 (仅在失败时存在)",
)
class HealthResponse(BaseModel):
"""健康检查响应"""
status: str = Field(..., description="服务状态: 'healthy''unhealthy'")
model_loaded: bool = Field(..., description="OCR 模型是否已加载")
version: str = Field(..., description="API 版本")