"""Backtesting API endpoints.""" from fastapi import APIRouter, HTTPException, Depends, BackgroundTasks from typing import Dict, Any from sqlalchemy import select import uuid from ..core.dependencies import get_backtesting_engine, get_strategy_registry from ..core.schemas import BacktestRequest, BacktestResponse from src.core.database import Strategy, get_database router = APIRouter() # Store running backtests _backtests: Dict[str, Dict[str, Any]] = {} @router.post("/run", response_model=BacktestResponse) async def run_backtest( backtest_data: BacktestRequest, background_tasks: BackgroundTasks, backtest_engine=Depends(get_backtesting_engine) ): """Run a backtest.""" try: db = get_database() async with db.get_session() as session: # Get strategy stmt = select(Strategy).where(Strategy.id == backtest_data.strategy_id) result = await session.execute(stmt) strategy_db = result.scalar_one_or_none() if not strategy_db: raise HTTPException(status_code=404, detail="Strategy not found") # Create strategy instance registry = get_strategy_registry() strategy_instance = registry.create_instance( strategy_id=strategy_db.id, name=strategy_db.class_name, parameters=strategy_db.parameters, timeframes=strategy_db.timeframes or [backtest_data.timeframe] ) if not strategy_instance: raise HTTPException(status_code=400, detail="Failed to create strategy instance") # Run backtest results = backtest_engine.run_backtest( strategy=strategy_instance, symbol=backtest_data.symbol, exchange=backtest_data.exchange, timeframe=backtest_data.timeframe, start_date=backtest_data.start_date, end_date=backtest_data.end_date, initial_capital=backtest_data.initial_capital, slippage=backtest_data.slippage, fee_rate=backtest_data.fee_rate ) if "error" in results: raise HTTPException(status_code=400, detail=results["error"]) return BacktestResponse( results=results, status="completed" ) except HTTPException: raise except Exception as e: raise HTTPException(status_code=500, detail=str(e)) @router.get("/results/{backtest_id}") async def get_backtest_results(backtest_id: str): """Get backtest results by ID.""" if backtest_id not in _backtests: raise HTTPException(status_code=404, detail="Backtest not found") return _backtests[backtest_id]