elmeg-demo/backend/routers/performances.py

93 lines
3.3 KiB
Python

from typing import List
from fastapi import APIRouter, Depends, HTTPException, Query
from sqlmodel import Session, select
from database import get_session
from models import Performance, PerformanceNickname, Tag, EntityTag
from schemas import PerformanceDetailRead, PerformanceNicknameCreate, PerformanceNicknameRead
from auth import get_current_user
router = APIRouter(prefix="/performances", tags=["performances"])
@router.get("/{performance_id}", response_model=PerformanceDetailRead)
def read_performance(performance_id: int, session: Session = Depends(get_session)):
performance = session.get(Performance, performance_id)
if not performance:
raise HTTPException(status_code=404, detail="Performance not found")
# --- Calculate Stats & Navigation ---
from sqlmodel import select, func, desc
from models import Show
# Get all performances of this song, ordered by date
# We need to join Show to order by date
all_perfs = session.exec(
select(Performance, Show.date)
.join(Show)
.where(Performance.song_id == performance.song_id)
.order_by(Show.date)
).all()
# Find current index
# all_perfs is a list of tuples (Performance, date)
current_index = -1
for i, (p, d) in enumerate(all_perfs):
if p.id == performance_id:
current_index = i
break
prev_id = None
next_id = None
gap = 0
times_played = current_index + 1 # 1-based count
if current_index > 0:
prev_id = all_perfs[current_index - 1][0].id
# Calculate Gap
# Gap is number of shows between prev performance and this one
prev_date = all_perfs[current_index - 1][1]
current_date = all_perfs[current_index][1]
gap = session.exec(
select(func.count(Show.id))
.where(Show.date > prev_date)
.where(Show.date < current_date)
).one()
if current_index < len(all_perfs) - 1:
next_id = all_perfs[current_index + 1][0].id
# Construct response manually to include extra fields
# We need to ensure nested models (show, song) are validated correctly
perf_dict = performance.model_dump()
perf_dict['show'] = performance.show
perf_dict['song'] = performance.song
perf_dict['nicknames'] = performance.nicknames
perf_dict['previous_performance_id'] = prev_id
perf_dict['next_performance_id'] = next_id
perf_dict['gap'] = gap
perf_dict['times_played'] = times_played
return perf_dict
@router.post("/{performance_id}/nicknames", response_model=PerformanceNicknameRead)
def suggest_nickname(
performance_id: int,
nickname: PerformanceNicknameCreate,
session: Session = Depends(get_session),
current_user = Depends(get_current_user)
):
# Check if performance exists
perf = session.get(Performance, performance_id)
if not perf:
raise HTTPException(status_code=404, detail="Performance not found")
db_nickname = PerformanceNickname.model_validate(nickname)
db_nickname.performance_id = performance_id
db_nickname.suggested_by = current_user.id
db_nickname.status = "pending" # Default to pending
session.add(db_nickname)
session.commit()
session.refresh(db_nickname)
return db_nickname