Files
my-v0-server/app/datafiles/base.py
T

57 lines
1.7 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
"""数据文件各环节共用的异常、上限和警告文案的写法"""
from collections.abc import Callable, Sequence
# 每张表的数据行数上限
MAX_TABLE_ROWS = 1_000_000
UNSUPPORTED_FORMAT = "不支持的文件格式,支持 CSV、TSV、Excel、JSON、JSONL、Parquet"
class DataFileError(Exception):
"""文件无法接收或解析;status 是返回给调用方的 HTTP 状态码,message 可以直接展示
解析在子进程里执行,异常要能跨进程传递,所以参数原样放进 args
"""
def __init__(self, status: int, message: str):
super().__init__(status, message)
self.status = status
self.message = message
def __str__(self) -> str:
return self.message
def where(sheet: str | None) -> str:
"""警告和错误信息的位置前缀:Excel 写 sheet 名,其他格式不写"""
return f"{sheet}:" if sheet else ""
def brief(items: Sequence[str], sep: str = "、", limit: int = 5) -> str:
"""警告里列举的内容最多写 limit 个,多出的用“等”概括"""
return sep.join(items[:limit]) + ("等" if len(items) > limit else "")
def rows_exceeded(sheet: str | None) -> DataFileError:
return DataFileError(
422, f"{where(sheet)}超过 {MAX_TABLE_ROWS // 10_000} 万行,请拆分后上传"
)
# 解析进度的回调:参数是当前环节内已完成的比例,0 到 1
Reporter = Callable[[float], None]
def no_report(fraction: float) -> None:
pass
def scaled(report: Reporter, start: float, end: float) -> Reporter:
"""把环节内的进度映射到上一级进度的 start 到 end 之间"""
def inner(fraction: float) -> None:
report(start + (end - start) * min(max(fraction, 0.0), 1.0))
return inner