Files
group_xinghuo_jinrong/app/api/market.py
T

109 lines
3.6 KiB
Python

"""Market alert and market data APIs."""
from __future__ import annotations
from datetime import date
from fastapi import APIRouter, Depends, Query, Request
from app.api.deps import get_auth_context, require_permission
from app.model.schemas import (
AuthContext,
MarketAlertFeedbackRequest,
MarketAlertGenerationRequest,
MarketAlertList,
MarketAlertScanRequest,
MarketAlertView,
)
from app.repository.market_alert_repository import MarketAlertRepository
from app.service.market_alert_feedback_service import MarketAlertFeedbackService
from app.service.market_alert_generation_service import MarketAlertGenerationService
from app.service.market_data_service import MarketDataService
from app.service.market_scan_service import MarketScanService
from app.utils.response import success_response
router = APIRouter()
fund_router = APIRouter()
AUTH_CONTEXT_DEP = Depends(get_auth_context)
MARKET_READ_DEP = Depends(require_permission("market_alert:read"))
MARKET_GENERATE_DEP = Depends(require_permission("market_alert:generate"))
MARKET_FEEDBACK_DEP = Depends(require_permission("market_alert:feedback"))
market_data_service = MarketDataService()
market_alert_repository = MarketAlertRepository()
market_scan_service = MarketScanService(repository=market_alert_repository)
market_alert_generation_service = MarketAlertGenerationService(repository=market_alert_repository)
market_alert_feedback_service = MarketAlertFeedbackService(repository=market_alert_repository)
@router.get("/ping")
def ping(request: Request, auth: AuthContext = AUTH_CONTEXT_DEP):
return success_response(request, {"module": "market", "status": "ready"})
@router.get("")
def list_market_alerts(
request: Request,
auth: AuthContext = MARKET_READ_DEP,
date: date | None = None,
status: str | None = None,
alert_type: str | None = None,
):
rows = market_alert_repository.list_alerts(nav_date=date, status=status, alert_type=alert_type)
result = MarketAlertList(items=[MarketAlertView.model_validate(row) for row in rows])
return success_response(request, result.model_dump(mode="json"))
@router.post("/scan")
def scan_market_alerts(
request: Request,
payload: MarketAlertScanRequest,
auth: AuthContext = MARKET_GENERATE_DEP,
):
result = market_scan_service.scan(
nav_date=payload.nav_date,
threshold_pct=payload.threshold_pct,
trace_id=request.state.trace_id,
)
return success_response(request, result.model_dump(mode="json"))
@router.post("/generate")
def generate_market_alert(
request: Request,
payload: MarketAlertGenerationRequest,
auth: AuthContext = MARKET_GENERATE_DEP,
):
result = market_alert_generation_service.generate(
fund_code=payload.fund_code,
trace_id=request.state.trace_id,
advisor_id=auth.advisor_id or auth.user_id,
)
return success_response(request, result.model_dump(mode="json"))
@router.put("/{alert_id}/feedback")
def feedback_market_alert(
alert_id: str,
request: Request,
payload: MarketAlertFeedbackRequest,
auth: AuthContext = MARKET_FEEDBACK_DEP,
):
result = market_alert_feedback_service.feedback(
alert_id=alert_id,
payload=payload,
auth=auth,
trace_id=request.state.trace_id,
)
return success_response(request, result.model_dump(mode="json"))
@fund_router.get("/fund/{fund_code}")
def get_fund_quote(
fund_code: str,
request: Request,
auth: AuthContext = MARKET_READ_DEP,
history_limit: int = Query(default=30, ge=1, le=365),
):
result = market_data_service.get_fund_quote(fund_code, history_limit=history_limit)
return success_response(request, result.model_dump(mode="json"))