fix: use dicts instead of pydantic models in manual serialization to prevent crashes
Some checks failed
Deploy Fediversion / deploy (push) Failing after 1s

This commit is contained in:
fullsizemalt 2026-01-01 02:37:58 -08:00
parent da72e89fd6
commit 3d090082fb

View file

@ -34,82 +34,87 @@ def create_show(
return db_show return db_show
def serialize_show(show: Show) -> ShowRead: def serialize_show(show: Show) -> dict:
""" """
Robustly serialize a Show object to ShowRead, manually handling relationships Robustly serialize a Show object to a dictionary.
to avoid infinite recursion in Pydantic v2/SQLModel. Returning a dict breaks the link to SQLAlchemy ORM objects completely,
preventing Pydantic from triggering lazy loads or infinite recursion during validation.
""" """
try: try:
# Base fields map directly # Base fields
s_read = ShowRead( data = {
id=show.id, "id": show.id,
date=show.date, "date": show.date,
slug=show.slug, "slug": show.slug,
vertical_id=show.vertical_id, "vertical_id": show.vertical_id,
venue_id=show.venue_id, "venue_id": show.venue_id,
tour_id=show.tour_id, "tour_id": show.tour_id,
notes=show.notes, "notes": show.notes,
bandcamp_link=show.bandcamp_link, "bandcamp_link": show.bandcamp_link,
nugs_link=show.nugs_link, "nugs_link": show.nugs_link,
youtube_link=show.youtube_link, "youtube_link": show.youtube_link,
# relisten_link is on model but not in ShowRead schema? "vertical": None,
# Check schema again if needed, but safe to omit if not in schema "venue": None,
) "tour": None,
"tags": [],
"performances": []
}
# Manually map relationships if present # Manually map relationships if present
if show.vertical: if show.vertical:
try: try:
s_read.vertical = VerticalSimple( data["vertical"] = {
id=show.vertical.id, "id": show.vertical.id,
name=show.vertical.name, "name": show.vertical.name,
slug=show.vertical.slug, "slug": show.vertical.slug,
description=show.vertical.description, "description": show.vertical.description,
logo_url=show.vertical.logo_url, "logo_url": show.vertical.logo_url,
accent_color=show.vertical.accent_color "accent_color": show.vertical.accent_color
) }
except Exception as e: except Exception as e:
print(f"Error serializing vertical for show {show.id}: {e}") print(f"Error serializing vertical for show {show.id}: {e}")
if show.venue: if show.venue:
try: try:
s_read.venue = VenueRead( data["venue"] = {
id=show.venue.id, "id": show.venue.id,
name=show.venue.name, "name": show.venue.name,
slug=show.venue.slug, "slug": show.venue.slug,
city=show.venue.city, "city": show.venue.city,
state=show.venue.state, "state": show.venue.state,
country=show.venue.country, "country": show.venue.country,
capacity=show.venue.capacity, "capacity": show.venue.capacity,
notes=show.venue.notes "notes": show.venue.notes
) }
except Exception as e: except Exception as e:
print(f"Error serializing venue for show {show.id}: {e}") print(f"Error serializing venue for show {show.id}: {e}")
if show.tour: if show.tour:
try: try:
s_read.tour = TourRead( data["tour"] = {
id=show.tour.id, "id": show.tour.id,
name=show.tour.name, "name": show.tour.name,
slug=show.tour.slug, "slug": show.tour.slug,
start_date=show.tour.start_date, "start_date": show.tour.start_date,
end_date=show.tour.end_date, "end_date": show.tour.end_date,
notes=show.tour.notes "notes": show.tour.notes
) }
except Exception as e: except Exception as e:
print(f"Error serializing tour for show {show.id}: {e}") print(f"Error serializing tour for show {show.id}: {e}")
return s_read return data
except Exception as e: except Exception as e:
print(f"CRITICAL Error serializing show {show.id}: {e}") print(f"CRITICAL Error serializing show {show.id}: {e}")
# Return a minimal valid object or None? # Return minimal valid dict
# Safest to return basic info without relationships so user sees something return {
return ShowRead( "id": show.id,
id=show.id, "date": show.date,
date=show.date, "vertical_id": show.vertical_id,
vertical_id=show.vertical_id, "slug": show.slug or "",
slug=show.slug or "" "tags": [],
) "performances": []
}
@router.get("/", response_model=PaginatedResponse[ShowRead]) @router.get("/", response_model=PaginatedResponse[ShowRead])
def read_shows( def read_shows(