from typing import Optional from datetime import datetime from pydantic import BaseModel, Field, model_validator class ReservationBaseDTO(BaseModel): classroom_id: int = Field(..., description="ID del aula asignada") commission_id: int = Field(..., description="ID de la comisión académica") user_id: int = Field(..., description="ID del docente responsable") start_time: datetime = Field(..., description="Fecha y hora de inicio") end_time: datetime = Field(..., description="Fecha y hora de finalización") purpose: str = Field(default="Clase regular", max_length=500, description="Motivo o título de la reserva") expected_attendees: int = Field(default=20, ge=1, description="Cantidad estimada de asistentes") shift: Optional[str] = Field(default=None, max_length=30, description="Turno (Mañana, Tarde, Vespertino, Noche)") virtual_link: Optional[str] = Field(default=None, max_length=500, description="Enlace a sala virtual (Meet/Zoom)") notes: Optional[str] = Field(default=None, description="Observaciones adicionales") status: Optional[str] = Field(default="PENDING", description="Estado de la reserva") @model_validator(mode='after') def validate_time_range(self): if self.end_time <= self.start_time: raise ValueError("La hora de finalización debe ser posterior a la hora de inicio.") return self class ReservationCreateDTO(ReservationBaseDTO): allow_co_teaching_exception: Optional[bool] = Field(default=False, description="Excepción justificada si hay co-docencia") class ReservationUpdateDTO(BaseModel): classroom_id: Optional[int] = None start_time: Optional[datetime] = None end_time: Optional[datetime] = None purpose: Optional[str] = None expected_attendees: Optional[int] = None shift: Optional[str] = None virtual_link: Optional[str] = None notes: Optional[str] = None status: Optional[str] = None allow_co_teaching_exception: Optional[bool] = False class ReservationResponseDTO(ReservationBaseDTO): id: int created_at: Optional[datetime] = None class Config: from_attributes = True