Phase 2.1: Card mirror system for deckbuilding features
- Created MtgCardMirror and DeckCardLink models in mirror_models.py - Created card_mirror_service.py with sync_mirrors functionality - Added sync_mirrors() method to mtgjson_manager.py - Added mirror_get_db() dependency to database.py - Added DecklistFile.status column (DRAUGHT/FINAL) - Updated DeckCreate schema with status field - Added DeckWithCardsResponse schema with card_count - Updated deck router to query card mirrors and return card counts - Added plain text deck content support
This commit is contained in:
@@ -1,18 +1,19 @@
|
||||
"""Deck management router endpoints."""
|
||||
from fastapi import APIRouter, Depends, HTTPException, status
|
||||
from sqlalchemy.ext.asyncio import AsyncSession
|
||||
from sqlalchemy import select, delete, update
|
||||
from sqlalchemy import select, delete, update, func
|
||||
from typing import Optional, List
|
||||
|
||||
from app.core.database import get_db
|
||||
from app.core.security import get_current_user
|
||||
from app.models.models import DecklistFile, DecklistFolder
|
||||
from app.schemas.schemas import DeckCreate, DeckUpdate, DeckResponse, FolderCreate, FolderResponse
|
||||
from app.models.mirror_models import DeckCardLink
|
||||
from app.schemas.schemas import DeckCreate, DeckUpdate, DeckResponse, DeckWithCardsResponse, FolderCreate, FolderResponse
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
@router.get("/", response_model=List[DeckResponse])
|
||||
@router.get("/", response_model=List[DeckWithCardsResponse])
|
||||
async def list_decks(
|
||||
folder_id: Optional[int] = None,
|
||||
page: int = 1,
|
||||
@@ -44,10 +45,24 @@ async def list_decks(
|
||||
result = await db.execute(stmt)
|
||||
decks = result.scalars().all()
|
||||
|
||||
return [DeckResponse.model_validate(deck) for deck in decks]
|
||||
# Include card counts for each deck
|
||||
deck_responses = []
|
||||
for deck in decks:
|
||||
# Get card count
|
||||
count_stmt = select(func.count()).select_from(DeckCardLink).where(
|
||||
DeckCardLink.deck_id == deck.id
|
||||
)
|
||||
count_result = await db.execute(count_stmt)
|
||||
card_count = count_result.scalar() or 0
|
||||
|
||||
deck_data = DeckWithCardsResponse.model_validate(deck)
|
||||
deck_data.card_count = card_count
|
||||
deck_responses.append(deck_data)
|
||||
|
||||
return deck_responses
|
||||
|
||||
|
||||
@router.post("/", response_model=DeckResponse)
|
||||
@router.post("/", response_model=DeckWithCardsResponse)
|
||||
async def create_deck(
|
||||
request: DeckCreate,
|
||||
db: AsyncSession = Depends(get_db),
|
||||
@@ -76,11 +91,15 @@ async def create_deck(
|
||||
name=request.name,
|
||||
content=request.content,
|
||||
format=request.format,
|
||||
status=request.status,
|
||||
)
|
||||
db.add(new_deck)
|
||||
await db.flush()
|
||||
|
||||
return DeckResponse.model_validate(new_deck)
|
||||
# Return with card count (0 for new deck)
|
||||
result = DeckWithCardsResponse.model_validate(new_deck)
|
||||
result.card_count = 0
|
||||
return result
|
||||
|
||||
|
||||
@router.get("/folders", response_model=List[FolderResponse])
|
||||
@@ -171,7 +190,7 @@ async def delete_folder(
|
||||
return {"message": "Folder deleted successfully"}
|
||||
|
||||
|
||||
@router.get("/{deck_id}", response_model=DeckResponse)
|
||||
@router.get("/{deck_id}", response_model=DeckWithCardsResponse)
|
||||
async def get_deck(
|
||||
deck_id: int,
|
||||
db: AsyncSession = Depends(get_db),
|
||||
@@ -193,10 +212,19 @@ async def get_deck(
|
||||
detail="Deck not found",
|
||||
)
|
||||
|
||||
return DeckResponse.model_validate(deck)
|
||||
# Get card count
|
||||
count_stmt = select(func.count()).select_from(DeckCardLink).where(
|
||||
DeckCardLink.deck_id == deck_id
|
||||
)
|
||||
count_result = await db.execute(count_stmt)
|
||||
card_count = count_result.scalar() or 0
|
||||
|
||||
result = DeckWithCardsResponse.model_validate(deck)
|
||||
result.card_count = card_count
|
||||
return result
|
||||
|
||||
|
||||
@router.patch("/{deck_id}", response_model=DeckResponse)
|
||||
@router.patch("/{deck_id}", response_model=DeckWithCardsResponse)
|
||||
async def update_deck(
|
||||
deck_id: int,
|
||||
request: DeckUpdate,
|
||||
@@ -235,7 +263,16 @@ async def update_deck(
|
||||
result = await db.execute(stmt)
|
||||
updated_deck = result.scalar_one_or_none()
|
||||
|
||||
return DeckResponse.model_validate(updated_deck)
|
||||
# Get card count
|
||||
count_stmt = select(func.count()).select_from(DeckCardLink).where(
|
||||
DeckCardLink.deck_id == deck_id
|
||||
)
|
||||
count_result = await db.execute(count_stmt)
|
||||
card_count = count_result.scalar() or 0
|
||||
|
||||
result = DeckWithCardsResponse.model_validate(updated_deck)
|
||||
result.card_count = card_count
|
||||
return result
|
||||
|
||||
|
||||
@router.delete("/{deck_id}")
|
||||
|
||||
Reference in New Issue
Block a user