80 lines
4.0 KiB
Python
80 lines
4.0 KiB
Python
from pydantic import BaseModel, Field, model_validator, field_validator, ConfigDict
|
||
from datetime import date
|
||
from typing import Optional
|
||
|
||
#id用cls_id来拼接生成,不用请求体过滤
|
||
#------------新增请求体-------------
|
||
class StudentCreate(BaseModel):
|
||
cls_id: int | str = Field(..., description="班级ID,6位数字")
|
||
name: str = Field(..., min_length=1, max_length=20, description="姓名")
|
||
gender: str = Field(..., min_length=1, max_length=1, description="性别")
|
||
age: int = Field(..., ge=1, le=100, description="年龄")
|
||
hometown: Optional[str] = Field(None, min_length=3, max_length=50, description="籍贯")
|
||
grad_school: str = Field(..., min_length=1, max_length=50, description="毕业院校")
|
||
major: str = Field(..., min_length=1, max_length=50, description="专业名称")
|
||
education: str = Field(..., min_length=1, max_length=20, description="学历")
|
||
enr_date: date = Field(..., description="入学日期")
|
||
grad_date: date = Field(..., description="毕业日期")
|
||
advisor_id: str = Field(..., min_length=1, max_length=15, description="顾问编号")
|
||
#校验入学时间必须比毕业时间小
|
||
@model_validator(mode='after')
|
||
def check_dates(self):
|
||
if self.grad_date <= self.enr_date:
|
||
raise ValueError("毕业日期必须晚于入学日期")
|
||
return self
|
||
# 校验传入的6位数是不是都是数字/都转化为字符串判断
|
||
@field_validator("cls_id", mode="before")
|
||
def convert_str(cls, v):
|
||
# 不管前端传数字还是字符串,统一转字符串
|
||
v = str(v)
|
||
if len(v) != 6 or not v.isdigit():
|
||
raise ValueError("班级ID必须是6位纯数字")
|
||
return v
|
||
#------------修改请求体-------------
|
||
class StudentUpdate(BaseModel):
|
||
cls_id: Optional[int|str] = Field(None, description="班级ID,6位数字")
|
||
name: Optional[str] = Field(None, min_length=1, max_length=20, description="姓名")
|
||
gender: Optional[str] = Field(None, min_length=1, max_length=1, description="性别")
|
||
age: Optional[int] = Field(None, ge=1, le=100, description="年龄")
|
||
hometown: Optional[str] = Field(None, min_length=3, max_length=50, description="籍贯")
|
||
grad_school: Optional[str] = Field(None, min_length=1, max_length=50, description="毕业院校")
|
||
major: Optional[str] = Field(None, min_length=1, max_length=50, description="专业名称")
|
||
education: Optional[str] = Field(None, min_length=1, max_length=20, description="学历")
|
||
enr_date: Optional[date]= Field(None, description="入学日期")
|
||
grad_date: Optional[date]= Field(None, description="毕业日期")
|
||
advisor_id: Optional[str] = Field(None, min_length=1, max_length=15, description="顾问编号")
|
||
|
||
@field_validator("cls_id", mode="before")
|
||
def convert_str(cls, v):
|
||
# 更新:不传cls_id(v=None)直接返回,跳过校验
|
||
if v is None:
|
||
return v
|
||
v = str(v)
|
||
if len(v) != 6 or not v.isdigit():
|
||
raise ValueError("班级ID必须是6位纯数字")
|
||
return v
|
||
|
||
@model_validator(mode='after')
|
||
def check_dates(self):
|
||
# 只在两个日期【都传了,不为None】的时候,才校验大小,传单个时在api层校验
|
||
if self.grad_date is not None and self.enr_date is not None:
|
||
if self.grad_date <= self.enr_date:
|
||
raise ValueError("毕业日期必须晚于入学日期")
|
||
return self
|
||
#--------------响应体模型--------------
|
||
class StudentResponse(BaseModel):
|
||
id: str
|
||
cls_id: str
|
||
name: str
|
||
gender: str
|
||
age: int
|
||
hometown: Optional[str]
|
||
grad_school: Optional[str]
|
||
major: Optional[str]
|
||
education: Optional[str]
|
||
enr_date: Optional[date]
|
||
grad_date: Optional[date]
|
||
advisor_id: Optional[str]
|
||
state: Optional[str]
|
||
|
||
model_config = ConfigDict(from_attributes=True) # 支持 ORM 对象转换 |