"""Portfolio endpoints.""" import logging from fastapi import APIRouter, HTTPException, Query, Request from sqlalchemy import select from sqlalchemy.exc import OperationalError from shared.sa_models import PositionRow logger = logging.getLogger(__name__) router = APIRouter() @router.get("/positions") async def get_positions(request: Request): """Get all current positions.""" try: db = request.app.state.db async with db.get_session() as session: result = await session.execute(select(PositionRow)) rows = result.scalars().all() return [ { "symbol": r.symbol, "quantity": float(r.quantity), "avg_entry_price": float(r.avg_entry_price), "current_price": float(r.current_price), "unrealized_pnl": float(r.quantity * (r.current_price - r.avg_entry_price)), } for r in rows ] except OperationalError as exc: logger.error("Database error fetching positions: %s", exc) raise HTTPException(status_code=503, detail="Database unavailable") from exc except Exception as exc: logger.error("Failed to get positions: %s", exc, exc_info=True) raise HTTPException(status_code=500, detail="Failed to retrieve positions") from exc @router.get("/snapshots") async def get_snapshots(request: Request, days: int = Query(30, ge=1, le=365)): """Get portfolio snapshots for the last N days.""" try: db = request.app.state.db snapshots = await db.get_portfolio_snapshots(days=days) return [ { "total_value": float(s["total_value"]), "realized_pnl": float(s["realized_pnl"]), "unrealized_pnl": float(s["unrealized_pnl"]), "snapshot_at": s["snapshot_at"].isoformat(), } for s in snapshots ] except OperationalError as exc: logger.error("Database error fetching snapshots: %s", exc) raise HTTPException(status_code=503, detail="Database unavailable") from exc except Exception as exc: logger.error("Failed to get snapshots: %s", exc, exc_info=True) raise HTTPException(status_code=500, detail="Failed to retrieve snapshots") from exc