import logging from typing import List, Optional from fastapi import APIRouter, Depends, HTTPException, Query from sqlalchemy import select from sqlalchemy.ext.asyncio import AsyncSession from app.database import get_db from app.models import Post from app.schemas import PriceImpact, TrumpPost router = APIRouter() logger = logging.getLogger(__name__) def _post_to_schema(post: Post) -> TrumpPost: price_impact: Optional[PriceImpact] = None if ( post.price_impact_asset and post.price_at_post is not None ): price_impact = PriceImpact( asset=post.price_impact_asset, m5=post.price_impact_m5 or 0.0, m15=post.price_impact_m15 or 0.0, m1h=post.price_impact_m1h or 0.0, price_at_post=post.price_at_post, ) return TrumpPost( id=post.id, text=post.text, source=post.source, published_at=post.published_at.isoformat(), sentiment=post.sentiment, signal=post.signal, ai_confidence=post.ai_confidence, ai_reasoning=post.ai_reasoning, relevant=post.relevant, price_impact=price_impact, ) @router.get("/posts", response_model=List[TrumpPost]) async def get_posts( limit: int = Query(default=20, ge=1, le=500), page: int = Query(default=1, ge=1), db: AsyncSession = Depends(get_db), ): offset = (page - 1) * limit result = await db.execute( select(Post).order_by(Post.published_at.desc()).offset(offset).limit(limit) ) posts = result.scalars().all() return [_post_to_schema(p) for p in posts] @router.get("/posts/{post_id}", response_model=TrumpPost) async def get_post(post_id: int, db: AsyncSession = Depends(get_db)): result = await db.execute(select(Post).where(Post.id == post_id)) post = result.scalar_one_or_none() if post is None: raise HTTPException(status_code=404, detail="Post not found") return _post_to_schema(post)