Bot commit: Добавлен файл models.py
This commit is contained in:
parent
f31d5221fd
commit
1d9fe9bfe3
450
models.py
Normal file
450
models.py
Normal file
@ -0,0 +1,450 @@
|
||||
from pydantic import BaseModel, Field, model_validator, validator, ConfigDict
|
||||
from typing import List, Optional, Literal
|
||||
from datetime import datetime, date, timezone
|
||||
from fastapi.security import OAuth2PasswordRequestForm
|
||||
import json
|
||||
from fastapi import File, Form, UploadFile
|
||||
|
||||
|
||||
class NotifyItem(BaseModel):
|
||||
user_id: str
|
||||
text: str
|
||||
title: Optional[str] = "Уведомление"
|
||||
link: str = "/profile"
|
||||
type_item: str = "c"
|
||||
|
||||
|
||||
class DeliverySendRequest(BaseModel):
|
||||
sender: str
|
||||
too: str
|
||||
item: str
|
||||
delivery_type: Literal["СДЭК", "Самостоятельно"]
|
||||
track: Optional[str] = Field(None, description="Трэк-номер для СДЭК")
|
||||
|
||||
|
||||
class DeliveryAcceptRequest(BaseModel):
|
||||
item: str
|
||||
|
||||
|
||||
class UserRegister(BaseModel):
|
||||
username: Optional[str]
|
||||
phone: Optional[str]
|
||||
email: Optional[str]
|
||||
# img: Optional[UploadFile]
|
||||
password: str
|
||||
client_id: str
|
||||
roles: List[str] = ["user"]
|
||||
extra_scopes: List[str] = []
|
||||
birthday: Optional[date]
|
||||
grade: Optional[str]
|
||||
female_name_lastname: Optional[str] = Field(None, alias="Female_Name_Lastame")
|
||||
living_place: Optional[str]
|
||||
offer_accepted: Optional[bool] = False
|
||||
offer_accepted_at: Optional[datetime] = None
|
||||
|
||||
@model_validator(mode='after')
|
||||
def at_least_one_identifier(self):
|
||||
if not any([self.username, self.phone, self.email]):
|
||||
raise ValueError("At least one of username, phone or email is required")
|
||||
return self
|
||||
model_config = {"validate_by_name": True}
|
||||
|
||||
|
||||
class FormCompetition(BaseModel):
|
||||
id: str
|
||||
title: str
|
||||
address: Optional[str]
|
||||
topic: Optional[str]
|
||||
short_desc: Optional[str]
|
||||
rules_file_id: Optional[str]
|
||||
poster_file_id: Optional[str]
|
||||
min_paintings: Optional[int]
|
||||
max_paintings: Optional[int]
|
||||
|
||||
|
||||
class UserLoginForm(OAuth2PasswordRequestForm):
|
||||
pass
|
||||
|
||||
|
||||
class LoginRequest(BaseModel):
|
||||
identifier: str
|
||||
password: str
|
||||
client_id: str
|
||||
|
||||
|
||||
class RestoreRequest(BaseModel):
|
||||
identifier: str
|
||||
next: str
|
||||
|
||||
|
||||
class ResetPasswordRequest(BaseModel):
|
||||
token: str
|
||||
new_password: str
|
||||
|
||||
|
||||
class AdminLoginRequest(BaseModel):
|
||||
user_id: str
|
||||
|
||||
|
||||
class PartnercompetitionRequest(BaseModel):
|
||||
competition_id: str
|
||||
post_id: str
|
||||
status: str
|
||||
|
||||
|
||||
class CompetitionArtistRequest(BaseModel):
|
||||
competition_id: str
|
||||
user_id: str
|
||||
|
||||
|
||||
class Partnercompetitionstop(BaseModel):
|
||||
competition_id: str
|
||||
|
||||
|
||||
class PartnerExhibitionDelete(BaseModel):
|
||||
exhibition_id: str
|
||||
|
||||
|
||||
class PostEditDescription(BaseModel):
|
||||
post_id: str
|
||||
description: str
|
||||
|
||||
|
||||
class TokenResponse(BaseModel):
|
||||
access_token: str
|
||||
refresh_token: str
|
||||
token_type: str = "bearer"
|
||||
|
||||
|
||||
class RefreshRequest(BaseModel):
|
||||
refresh_token: str | None = None
|
||||
client_id: str | None = None
|
||||
|
||||
|
||||
class CompetitionCreate(BaseModel):
|
||||
datetime_start: datetime
|
||||
date_finish: datetime
|
||||
poster: UploadFile
|
||||
type_: str
|
||||
title: str
|
||||
topic: Optional[str] = None
|
||||
nominations: List[str] = []
|
||||
address: str
|
||||
short_desc: Optional[str] = None
|
||||
rules_link: Optional[str] = None
|
||||
rules: Optional[UploadFile] = None
|
||||
min_paintings: int
|
||||
max_paintings: int
|
||||
emailsNotify: bool = False
|
||||
serviceSocial: bool = False
|
||||
userSocial: bool = False
|
||||
|
||||
@model_validator(mode="after")
|
||||
def make_aware(cls, values):
|
||||
tz = timezone.utc
|
||||
if not values.rules_link and not values.rules:
|
||||
raise ValueError(
|
||||
"Укажите хотя бы один из параметров: `rules_link` ИЛИ `rules` (файл)."
|
||||
)
|
||||
if values.datetime_start and values.datetime_start.tzinfo is None:
|
||||
values.datetime_start = values.datetime_start.replace(tzinfo=tz)
|
||||
elif values.datetime_start:
|
||||
values.datetime_start = values.datetime_start.astimezone(tz)
|
||||
if values.date_finish and values.date_finish.tzinfo is None:
|
||||
values.date_finish = values.date_finish.replace(tzinfo=tz)
|
||||
elif values.date_finish:
|
||||
values.date_finish = values.date_finish.astimezone(tz)
|
||||
return values
|
||||
|
||||
@validator("nominations", pre=True, always=True)
|
||||
def parse_nominations(cls, v):
|
||||
if v is None:
|
||||
return None
|
||||
if isinstance(v, list):
|
||||
return v
|
||||
try:
|
||||
data = json.loads(v)
|
||||
return data if isinstance(data, list) else [data]
|
||||
except (json.JSONDecodeError, TypeError):
|
||||
return [v]
|
||||
|
||||
|
||||
class ExhibitionCreate(BaseModel):
|
||||
datetime_start: datetime
|
||||
date_finish: datetime
|
||||
poster: UploadFile
|
||||
rules: Optional[UploadFile] = None
|
||||
rules_link: Optional[str] = None
|
||||
tizer: Optional[UploadFile] = None
|
||||
tizer_link: Optional[str] = None
|
||||
title: str
|
||||
topic: Optional[str] = None
|
||||
address: Optional[str] = None
|
||||
place: Optional[str] = None
|
||||
|
||||
@model_validator(mode="after")
|
||||
def make_aware(cls, values):
|
||||
tz = timezone.utc
|
||||
if not values.rules_link and not values.rules:
|
||||
raise ValueError(
|
||||
"Укажите хотя бы один из параметров: `rules_link` ИЛИ `rules` (файл)."
|
||||
)
|
||||
if not values.tizer_link and not values.tizer:
|
||||
raise ValueError(
|
||||
"Укажите хотя бы один из параметров: `tizer_link` ИЛИ `tizer` (файл)."
|
||||
)
|
||||
if values.datetime_start and values.datetime_start.tzinfo is None:
|
||||
values.datetime_start = values.datetime_start.replace(tzinfo=tz)
|
||||
elif values.datetime_start:
|
||||
values.datetime_start = values.datetime_start.astimezone(tz)
|
||||
if values.date_finish and values.date_finish.tzinfo is None:
|
||||
values.date_finish = values.date_finish.replace(tzinfo=tz)
|
||||
elif values.date_finish:
|
||||
values.date_finish = values.date_finish.astimezone(tz)
|
||||
return values
|
||||
|
||||
|
||||
async def build_payload(
|
||||
datetime_start: datetime = Form(...),
|
||||
date_finish: datetime = Form(...),
|
||||
poster: UploadFile = File(...),
|
||||
type_: str = Form(...),
|
||||
title: str = Form(...),
|
||||
topic: Optional[str] = Form(None),
|
||||
nominations: Optional[str] = Form(None),
|
||||
address: str = Form(...),
|
||||
short_desc: Optional[str] = Form(None),
|
||||
rules_link: Optional[str] = Form(None),
|
||||
rules: Optional[UploadFile] = File(None),
|
||||
min_paintings: int = Form(...),
|
||||
max_paintings: int = Form(...),
|
||||
emailsNotify: bool = Form(False),
|
||||
serviceSocial: bool = Form(False),
|
||||
userSocial: bool = Form(False),
|
||||
) -> CompetitionCreate:
|
||||
return CompetitionCreate(
|
||||
datetime_start=datetime_start,
|
||||
date_finish=date_finish,
|
||||
poster=poster,
|
||||
type_=type_,
|
||||
title=title,
|
||||
topic=topic,
|
||||
nominations=nominations,
|
||||
address=address,
|
||||
short_desc=short_desc,
|
||||
rules_link=rules_link,
|
||||
rules=rules,
|
||||
min_paintings=min_paintings,
|
||||
max_paintings=max_paintings,
|
||||
emailsNotify=emailsNotify,
|
||||
serviceSocial=serviceSocial,
|
||||
userSocial=userSocial,
|
||||
)
|
||||
|
||||
|
||||
class CompetitionUpdate(BaseModel):
|
||||
datetime_start: Optional[datetime] = None
|
||||
date_finish: Optional[datetime] = None
|
||||
poster: Optional[UploadFile] = None
|
||||
type_: Optional[str] = None
|
||||
title: Optional[str] = None
|
||||
topic: Optional[str] = None
|
||||
nominations: Optional[List[str]] = None
|
||||
rules_link: Optional[str] = None
|
||||
address: Optional[str] = None
|
||||
short_desc: Optional[str] = None
|
||||
rules: Optional[UploadFile] = None
|
||||
min_paintings: Optional[int] = None
|
||||
max_paintings: Optional[int] = None
|
||||
emailsNotify: Optional[bool] = False
|
||||
serviceSocial: Optional[bool] = False
|
||||
userSocial: Optional[bool] = False
|
||||
|
||||
model_config = ConfigDict(
|
||||
arbitrary_types_allowed=True,
|
||||
json_encoders={
|
||||
datetime: lambda v: v.isoformat()
|
||||
},
|
||||
)
|
||||
|
||||
@model_validator(mode="after")
|
||||
def make_aware(cls, values):
|
||||
tz = timezone.utc
|
||||
if values.datetime_start and values.datetime_start.tzinfo is None:
|
||||
values.datetime_start = values.datetime_start.replace(tzinfo=tz)
|
||||
elif values.datetime_start:
|
||||
values.datetime_start = values.datetime_start.astimezone(tz)
|
||||
if values.date_finish and values.date_finish.tzinfo is None:
|
||||
values.date_finish = values.date_finish.replace(tzinfo=tz)
|
||||
elif values.date_finish:
|
||||
values.date_finish = values.date_finish.astimezone(tz)
|
||||
return values
|
||||
|
||||
|
||||
@validator("nominations", pre=True, always=True)
|
||||
def parse_nominations(cls, v):
|
||||
if v is None:
|
||||
return None
|
||||
if isinstance(v, list):
|
||||
return v
|
||||
try:
|
||||
data = json.loads(v)
|
||||
return data if isinstance(data, list) else [data]
|
||||
except (json.JSONDecodeError, TypeError):
|
||||
return [v]
|
||||
|
||||
|
||||
async def build_update_payload(
|
||||
datetime_start: Optional[datetime] = Form(None),
|
||||
date_finish: Optional[datetime] = Form(None),
|
||||
poster: Optional[UploadFile] = File(None),
|
||||
type_: Optional[str] = Form(...),
|
||||
title: Optional[str] = Form(None),
|
||||
topic: Optional[str] = Form(None),
|
||||
nominations: Optional[str] = Form(None),
|
||||
rules_link: Optional[str] = Form(None),
|
||||
address: Optional[str] = Form(None),
|
||||
short_desc: Optional[str] = Form(None),
|
||||
rules: Optional[UploadFile] = File(None),
|
||||
min_paintings: Optional[int] = Form(None),
|
||||
max_paintings: Optional[int] = Form(None),
|
||||
emailsNotify: Optional[bool] = Form(False),
|
||||
serviceSocial: Optional[bool] = Form(False),
|
||||
userSocial: Optional[bool] = Form(False),
|
||||
) -> CompetitionUpdate:
|
||||
return CompetitionUpdate(
|
||||
datetime_start=datetime_start,
|
||||
date_finish=date_finish,
|
||||
poster=poster,
|
||||
type_=type_,
|
||||
title=title,
|
||||
topic=topic,
|
||||
nominations=nominations,
|
||||
rules_link=rules_link,
|
||||
address=address,
|
||||
short_desc=short_desc,
|
||||
rules=rules,
|
||||
min_paintings=min_paintings,
|
||||
max_paintings=max_paintings,
|
||||
emailsNotify=emailsNotify,
|
||||
serviceSocial=serviceSocial,
|
||||
userSocial=userSocial,
|
||||
)
|
||||
|
||||
|
||||
class CompetitionPublishParams(BaseModel):
|
||||
competition_id: str
|
||||
emailsNotify: bool = False
|
||||
serviceSocial: bool = False
|
||||
userSocial: bool = False
|
||||
usersSocial: bool = False
|
||||
|
||||
|
||||
async def build_publish_payload(
|
||||
competition_id: str = Form(...),
|
||||
emailsNotify: bool = Form(False),
|
||||
serviceSocial: bool = Form(False),
|
||||
userSocial: bool = Form(False),
|
||||
usersSocial: bool = Form(False),
|
||||
) -> CompetitionPublishParams:
|
||||
return CompetitionPublishParams(
|
||||
competition_id=competition_id,
|
||||
emailsNotify=emailsNotify,
|
||||
serviceSocial=serviceSocial,
|
||||
userSocial=userSocial,
|
||||
usersSocial=usersSocial,
|
||||
)
|
||||
|
||||
|
||||
async def build_exhibition_payload(
|
||||
datetime_start: datetime = Form(...),
|
||||
date_finish: datetime = Form(...),
|
||||
poster: Optional[UploadFile] = File(...),
|
||||
rules: Optional[UploadFile] = File(None),
|
||||
rules_link: Optional[str] = Form(None),
|
||||
tizer: Optional[UploadFile] = File(None),
|
||||
tizer_link: Optional[str] = Form(None),
|
||||
title: str = Form(...),
|
||||
topic: Optional[str] = Form(None),
|
||||
address: Optional[str] = Form(None),
|
||||
place: Optional[str] = Form(None),
|
||||
) -> ExhibitionCreate:
|
||||
return ExhibitionCreate(
|
||||
datetime_start=datetime_start,
|
||||
date_finish=date_finish,
|
||||
poster=poster,
|
||||
rules=rules,
|
||||
rules_link=rules_link,
|
||||
tizer=tizer,
|
||||
tizer_link=tizer_link,
|
||||
title=title,
|
||||
topic=topic,
|
||||
address=address,
|
||||
place=place,
|
||||
)
|
||||
|
||||
|
||||
class ExhibitionUpdate(BaseModel):
|
||||
datetime_start: Optional[datetime] = None
|
||||
date_finish: Optional[datetime] = None
|
||||
poster: Optional[UploadFile] = None
|
||||
rules: Optional[UploadFile] = None
|
||||
rules_link: Optional[str] = None
|
||||
tizer: Optional[UploadFile] = None
|
||||
tizer_link: Optional[str] = None
|
||||
title: Optional[str] = None
|
||||
topic: Optional[str] = None
|
||||
address: Optional[str] = None
|
||||
place: Optional[str] = None
|
||||
short_desc: Optional[str] = None
|
||||
|
||||
model_config = ConfigDict(
|
||||
arbitrary_types_allowed=True,
|
||||
json_encoders={
|
||||
datetime: lambda v: v.isoformat()
|
||||
},
|
||||
)
|
||||
|
||||
@model_validator(mode="after")
|
||||
def make_aware(cls, values):
|
||||
tz = timezone.utc
|
||||
if values.datetime_start and values.datetime_start.tzinfo is None:
|
||||
values.datetime_start = values.datetime_start.replace(tzinfo=tz)
|
||||
elif values.datetime_start:
|
||||
values.datetime_start = values.datetime_start.astimezone(tz)
|
||||
|
||||
if values.date_finish and values.date_finish.tzinfo is None:
|
||||
values.date_finish = values.date_finish.replace(tzinfo=tz)
|
||||
elif values.date_finish:
|
||||
values.date_finish = values.date_finish.astimezone(tz)
|
||||
return values
|
||||
|
||||
|
||||
async def build_update_exhibition_payload(
|
||||
datetime_start: Optional[datetime] = Form(None),
|
||||
date_finish: Optional[datetime] = Form(None),
|
||||
poster: Optional[UploadFile] = File(None),
|
||||
rules: Optional[UploadFile] = File(None),
|
||||
rules_link: Optional[str] = Form(None),
|
||||
tizer: Optional[UploadFile] = File(None),
|
||||
tizer_link: Optional[str] = Form(None),
|
||||
title: Optional[str] = Form(None),
|
||||
topic: Optional[str] = Form(None),
|
||||
address: Optional[str] = Form(None),
|
||||
place: Optional[str] = Form(None),
|
||||
short_desc: Optional[str] = Form(None),
|
||||
) -> ExhibitionUpdate:
|
||||
return ExhibitionUpdate(
|
||||
datetime_start=datetime_start,
|
||||
date_finish=date_finish,
|
||||
poster=poster,
|
||||
rules=rules,
|
||||
rules_link=rules_link,
|
||||
tizer=tizer,
|
||||
tizer_link=tizer_link,
|
||||
title=title,
|
||||
topic=topic,
|
||||
address=address,
|
||||
place=place,
|
||||
short_desc=short_desc,
|
||||
)
|
||||
Loading…
Reference in New Issue
Block a user