Files
you-music/backend/app/api/playlist.py
T
2025-10-30 14:45:41 +11:00

171 lines
5.2 KiB
Python

from fastapi import APIRouter, Depends, HTTPException
from sqlalchemy.ext.asyncio import AsyncSession
from sqlalchemy import select
from typing import List
from app.db.session import get_db
from app.models.models import Playlist, Music, playlist_music
from app.schemas.schemas import Playlist as PlaylistSchema, PlaylistCreate, PlaylistUpdate
router = APIRouter()
@router.get("/", response_model=List[PlaylistSchema])
async def get_playlists(db: AsyncSession = Depends(get_db)):
"""Get all playlists"""
result = await db.execute(select(Playlist))
playlists = result.scalars().all()
return playlists
@router.post("/", response_model=PlaylistSchema)
async def create_playlist(
playlist: PlaylistCreate,
db: AsyncSession = Depends(get_db)
):
"""Create a new playlist"""
# Check if playlist with same name exists
result = await db.execute(
select(Playlist).where(Playlist.name == playlist.name)
)
existing = result.scalar_one_or_none()
if existing:
raise HTTPException(status_code=400, detail="Playlist already exists")
db_playlist = Playlist(**playlist.model_dump())
db.add(db_playlist)
await db.commit()
await db.refresh(db_playlist)
return db_playlist
@router.get("/{playlist_id}", response_model=PlaylistSchema)
async def get_playlist(playlist_id: int, db: AsyncSession = Depends(get_db)):
"""Get a specific playlist with all its music"""
result = await db.execute(
select(Playlist).where(Playlist.id == playlist_id)
)
playlist = result.scalar_one_or_none()
if not playlist:
raise HTTPException(status_code=404, detail="Playlist not found")
return playlist
@router.put("/{playlist_id}", response_model=PlaylistSchema)
async def update_playlist(
playlist_id: int,
playlist_update: PlaylistUpdate,
db: AsyncSession = Depends(get_db)
):
"""Update playlist details"""
result = await db.execute(
select(Playlist).where(Playlist.id == playlist_id)
)
playlist = result.scalar_one_or_none()
if not playlist:
raise HTTPException(status_code=404, detail="Playlist not found")
for field, value in playlist_update.model_dump(exclude_unset=True).items():
setattr(playlist, field, value)
await db.commit()
await db.refresh(playlist)
return playlist
@router.delete("/{playlist_id}")
async def delete_playlist(playlist_id: int, db: AsyncSession = Depends(get_db)):
"""Delete a playlist"""
result = await db.execute(
select(Playlist).where(Playlist.id == playlist_id)
)
playlist = result.scalar_one_or_none()
if not playlist:
raise HTTPException(status_code=404, detail="Playlist not found")
await db.delete(playlist)
await db.commit()
return {"message": "Playlist deleted successfully"}
@router.post("/{playlist_id}/music/{music_id}")
async def add_music_to_playlist(
playlist_id: int,
music_id: int,
db: AsyncSession = Depends(get_db)
):
"""Add music to playlist"""
# Get playlist
result = await db.execute(
select(Playlist).where(Playlist.id == playlist_id)
)
playlist = result.scalar_one_or_none()
if not playlist:
raise HTTPException(status_code=404, detail="Playlist not found")
# Get music
result = await db.execute(
select(Music).where(Music.id == music_id)
)
music = result.scalar_one_or_none()
if not music:
raise HTTPException(status_code=404, detail="Music not found")
# Check if already in playlist
if music in playlist.music_items:
raise HTTPException(status_code=400, detail="Music already in playlist")
# Add to playlist
playlist.music_items.append(music)
await db.commit()
return {"message": "Music added to playlist"}
@router.delete("/{playlist_id}/music/{music_id}")
async def remove_music_from_playlist(
playlist_id: int,
music_id: int,
db: AsyncSession = Depends(get_db)
):
"""Remove music from playlist"""
# Get playlist
result = await db.execute(
select(Playlist).where(Playlist.id == playlist_id)
)
playlist = result.scalar_one_or_none()
if not playlist:
raise HTTPException(status_code=404, detail="Playlist not found")
# Get music
result = await db.execute(
select(Music).where(Music.id == music_id)
)
music = result.scalar_one_or_none()
if not music:
raise HTTPException(status_code=404, detail="Music not found")
# Remove from playlist
if music in playlist.music_items:
playlist.music_items.remove(music)
await db.commit()
return {"message": "Music removed from playlist"}
else:
raise HTTPException(status_code=404, detail="Music not in playlist")
@router.get("/name/{playlist_name}", response_model=PlaylistSchema)
async def get_playlist_by_name(
playlist_name: str,
db: AsyncSession = Depends(get_db)
):
"""Get playlist by name"""
result = await db.execute(
select(Playlist).where(Playlist.name == playlist_name)
)
playlist = result.scalar_one_or_none()
if not playlist:
raise HTTPException(status_code=404, detail="Playlist not found")
return playlist