from datetime import datetime from fastapi import APIRouter, Depends, HTTPException, Query from sqlalchemy.ext.asyncio import AsyncSession from backend.database import get_db from backend.schemas.post import PostResponse, PostDetailResponse from backend.services import post_service from backend.models.metric_snapshot import MetricSnapshot from sqlalchemy import select router = APIRouter(prefix="/posts", tags=["posts"]) @router.get("") async def list_posts( subreddit_id: int | None = None, author: str | None = None, flair: str | None = None, sort_by: str = Query("created_utc", pattern="^(created_utc|score|num_comments)$"), sort_order: str = Query("desc", pattern="^(asc|desc)$"), since: datetime | None = None, until: datetime | None = None, page: int = Query(1, ge=1), per_page: int = Query(25, ge=1, le=100), db: AsyncSession = Depends(get_db), ): posts, total = await post_service.list_posts( db, subreddit_id, author, flair, sort_by, sort_order, since, until, page, per_page ) return { "data": posts, "total": total, "page": page, "per_page": per_page, "pages": (total + per_page - 1) // per_page if per_page else 0, } @router.get("/{post_id}") async def get_post(post_id: int, db: AsyncSession = Depends(get_db)): post = await post_service.get_post(db, post_id) if not post: raise HTTPException(status_code=404, detail="Post not found") return post @router.get("/{post_id}/snapshots") async def get_post_snapshots(post_id: int, db: AsyncSession = Depends(get_db)): stmt = ( select(MetricSnapshot) .where(MetricSnapshot.post_id == post_id) .order_by(MetricSnapshot.snapshot_at.asc()) ) result = await db.execute(stmt) snapshots = result.scalars().all() return [ { "score": s.score, "num_comments": s.num_comments, "upvote_ratio": s.upvote_ratio, "snapshot_at": s.snapshot_at, } for s in snapshots ]