stock-ai-agent/backend/app/api/news.py
2026-02-25 19:59:20 +08:00

180 lines
4.7 KiB
Python

"""
新闻 API - 提供新闻查询接口
"""
from fastapi import APIRouter, HTTPException, Query
from typing import Dict, List, Optional, Any
from app.news_agent.news_agent import get_news_agent
from app.news_agent.news_db_service import get_news_db_service
from app.utils.logger import logger
router = APIRouter(prefix="/api/news", tags=["新闻管理"])
@router.get("/articles")
async def get_articles(
category: Optional[str] = Query(None, description="分类过滤 (crypto/stock)"),
limit: int = Query(50, ge=1, le=200, description="返回数量限制"),
hours: int = Query(24, ge=1, le=168, description="查询最近多少小时")
) -> Dict[str, Any]:
"""
获取新闻文章列表
Args:
category: 分类过滤
limit: 返回数量限制
hours: 查询最近多少小时
Returns:
文章列表
"""
try:
db_service = get_news_db_service()
articles = db_service.get_latest_articles(
category=category,
limit=limit,
hours=hours
)
return {
'success': True,
'articles': articles,
'count': len(articles)
}
except Exception as e:
logger.error(f"获取新闻文章失败: {e}")
raise HTTPException(status_code=500, detail=str(e))
@router.get("/stats")
async def get_news_stats(
hours: int = Query(24, ge=1, le=168, description="统计最近多少小时")
) -> Dict[str, Any]:
"""
获取新闻统计信息
Args:
hours: 统计最近多少小时
Returns:
统计数据
"""
try:
news_agent = get_news_agent()
agent_stats = news_agent.get_stats()
db_service = get_news_db_service()
db_stats = db_service.get_stats(hours=hours)
return {
'success': True,
'agent': agent_stats,
'database': db_stats
}
except Exception as e:
logger.error(f"获取新闻统计失败: {e}")
raise HTTPException(status_code=500, detail=str(e))
@router.post("/fetch")
async def manual_fetch(
category: Optional[str] = Query(None, description="分类过滤 (crypto/stock)")
) -> Dict[str, Any]:
"""
手动触发新闻抓取
Args:
category: 分类过滤
Returns:
抓取结果
"""
try:
news_agent = get_news_agent()
result = await news_agent.manual_fetch(category)
return {
'success': True,
**result
}
except Exception as e:
logger.error(f"手动抓取新闻失败: {e}")
raise HTTPException(status_code=500, detail=str(e))
@router.get("/high-priority")
async def get_high_priority_articles(
limit: int = Query(20, ge=1, le=100, description="返回数量限制"),
min_priority: float = Query(40.0, description="最低优先级分数"),
hours: int = Query(24, ge=1, le=168, description="查询最近多少小时")
) -> Dict[str, Any]:
"""
获取高优先级文章
Args:
limit: 返回数量限制
min_priority: 最低优先级分数
hours: 查询最近多少小时
Returns:
高优先级文章列表
"""
try:
db_service = get_news_db_service()
articles = db_service.get_high_priority_articles(
limit=limit,
min_priority=min_priority,
hours=hours
)
return {
'success': True,
'articles': [article.to_dict() for article in articles],
'count': len(articles)
}
except Exception as e:
logger.error(f"获取高优先级文章失败: {e}")
raise HTTPException(status_code=500, detail=str(e))
@router.get("/sources")
async def get_news_sources() -> Dict[str, Any]:
"""
获取新闻源配置
Returns:
新闻源列表
"""
try:
from app.news_agent.sources import CRYPTO_NEWS_SOURCES, STOCK_NEWS_SOURCES
# 只返回基本信息,隐藏敏感配置
crypto_sources = [
{
'name': s['name'],
'category': s['category'],
'enabled': s['enabled']
}
for s in CRYPTO_NEWS_SOURCES
]
stock_sources = [
{
'name': s['name'],
'category': s['category'],
'enabled': s['enabled']
}
for s in STOCK_NEWS_SOURCES
]
return {
'success': True,
'crypto': crypto_sources,
'stock': stock_sources,
'total': len(crypto_sources) + len(stock_sources)
}
except Exception as e:
logger.error(f"获取新闻源失败: {e}")
raise HTTPException(status_code=500, detail=str(e))