generated from gilles/template-webapp
import ali
This commit is contained in:
@@ -5,8 +5,9 @@ Définit les schémas de validation pour les requêtes et réponses API.
|
||||
|
||||
from datetime import date, datetime
|
||||
from decimal import Decimal
|
||||
from typing import Any
|
||||
|
||||
from pydantic import BaseModel, ConfigDict, Field
|
||||
from pydantic import BaseModel, ConfigDict, Field, model_validator
|
||||
|
||||
from app.models.item import ItemStatus
|
||||
from app.schemas.category import CategoryResponse
|
||||
@@ -26,6 +27,7 @@ class ItemBase(BaseModel):
|
||||
url: str | None = Field(None, max_length=500, description="Lien vers page produit")
|
||||
price: Decimal | None = Field(None, ge=0, decimal_places=2, description="Prix d'achat")
|
||||
purchase_date: date | None = Field(None, description="Date d'achat")
|
||||
characteristics: dict[str, str] | None = Field(None, description="Caractéristiques techniques (clé-valeur)")
|
||||
notes: str | None = Field(None, description="Notes libres")
|
||||
|
||||
|
||||
@@ -34,6 +36,8 @@ class ItemCreate(ItemBase):
|
||||
|
||||
category_id: int = Field(..., description="ID de la catégorie")
|
||||
location_id: int = Field(..., description="ID de l'emplacement")
|
||||
parent_item_id: int | None = Field(None, description="ID de l'objet parent (si intégré)")
|
||||
shop_id: int | None = Field(None, description="ID de la boutique d'achat")
|
||||
|
||||
|
||||
class ItemUpdate(BaseModel):
|
||||
@@ -49,9 +53,12 @@ class ItemUpdate(BaseModel):
|
||||
url: str | None = Field(None, max_length=500)
|
||||
price: Decimal | None = Field(None, ge=0)
|
||||
purchase_date: date | None = None
|
||||
characteristics: dict[str, str] | None = None
|
||||
notes: str | None = None
|
||||
category_id: int | None = None
|
||||
location_id: int | None = None
|
||||
parent_item_id: int | None = None
|
||||
shop_id: int | None = None
|
||||
|
||||
|
||||
class ItemResponse(ItemBase):
|
||||
@@ -62,6 +69,8 @@ class ItemResponse(ItemBase):
|
||||
id: int
|
||||
category_id: int
|
||||
location_id: int
|
||||
parent_item_id: int | None = None
|
||||
shop_id: int | None = None
|
||||
created_at: datetime
|
||||
updated_at: datetime
|
||||
|
||||
@@ -71,6 +80,57 @@ class ItemWithRelations(ItemResponse):
|
||||
|
||||
category: CategoryResponse
|
||||
location: LocationResponse
|
||||
thumbnail_id: int | None = None
|
||||
parent_item_name: str | None = None
|
||||
|
||||
@model_validator(mode="before")
|
||||
@classmethod
|
||||
def extract_computed_fields(cls, data: Any) -> Any:
|
||||
"""Extrait les champs calculés : thumbnail et nom du parent."""
|
||||
from sqlalchemy.orm import InstanceState
|
||||
|
||||
thumbnail_id = None
|
||||
parent_item_name = None
|
||||
|
||||
# Vérifier que les relations sont chargées (éviter lazy load en async)
|
||||
loaded_relations: set[str] = set()
|
||||
if hasattr(data, "_sa_instance_state"):
|
||||
state: InstanceState = data._sa_instance_state
|
||||
loaded_relations = set(state.dict.keys())
|
||||
|
||||
if "documents" in loaded_relations:
|
||||
for doc in data.documents:
|
||||
if doc.type.value == "photo":
|
||||
thumbnail_id = doc.id
|
||||
break
|
||||
|
||||
if "parent_item" in loaded_relations and data.parent_item is not None:
|
||||
parent_item_name = data.parent_item.name
|
||||
|
||||
if isinstance(data, dict):
|
||||
if thumbnail_id:
|
||||
data["thumbnail_id"] = thumbnail_id
|
||||
if parent_item_name:
|
||||
data["parent_item_name"] = parent_item_name
|
||||
elif thumbnail_id or parent_item_name:
|
||||
result = {}
|
||||
for k in dir(data):
|
||||
if k.startswith("_"):
|
||||
continue
|
||||
# Ne pas accéder aux relations non chargées
|
||||
if k in ("documents", "parent_item", "children", "shop"):
|
||||
continue
|
||||
try:
|
||||
result[k] = getattr(data, k)
|
||||
except Exception:
|
||||
pass
|
||||
if thumbnail_id:
|
||||
result["thumbnail_id"] = thumbnail_id
|
||||
if parent_item_name:
|
||||
result["parent_item_name"] = parent_item_name
|
||||
return result
|
||||
|
||||
return data
|
||||
|
||||
|
||||
class ItemSummary(BaseModel):
|
||||
|
||||
Reference in New Issue
Block a user