feat: 实现回测功能
## 功能概述 实现完整的回测功能,支持基于历史数据模拟跟单策略的执行效果。 ## 后端实现 - 数据库:新增 backtest_task 和 backtest_trade 表(V27迁移脚本) - 实体类:BacktestTask、BacktestTrade - Repository:BacktestTaskRepository、BacktestTradeRepository - Service: - BacktestService:回测任务管理(CRUD) - BacktestDataService:从 Polymarket Data API 获取历史交易数据 - BacktestExecutionService:回测算法核心实现 - BacktestPollingService:定时轮询执行回测任务 - Controller:BacktestController(6个API接口) - DTO:BacktestDto、TradeData - 错误码:新增回测相关错误码和国际化消息 ## 前端实现 - 页面组件: - BacktestList:回测任务列表 - BacktestCreate:创建回测任务 - BacktestDetail:回测详情(含图表) - BacktestChart:资金曲线图表(使用 ECharts) - 类型定义:backtest.ts - API 服务:集成所有回测接口 - 国际化:支持中英文 ## 核心特性 - 回测天数限制:1-15 天 - 数据获取:直接从 Polymarket Data API 获取历史交易(不使用缓存表) - 任务执行:同一时刻只执行一个任务,按创建时间顺序执行最早创建的任务 - 回测算法:完整实现市场结算、卖出匹配、价格容忍度、每日订单限制等规则 - 实时进度:支持任务进度更新和实时轮询 ## 文档更新 - BACKTEST_PRD.md:产品需求文档 - BACKTEST_TECHNICAL_DESIGN.md:技术设计文档 - BACKTEST_REVIEW_CHECKLIST.md:设计评审检查清单 ## 其他修改 - 移除 max_position_count 配置(V26迁移脚本) - 移除 BacktestSyncService(不再需要实时同步) - 修复前后端编译错误
This commit is contained in:
@@ -0,0 +1,205 @@
|
||||
/**
|
||||
* 回测相关类型定义
|
||||
*/
|
||||
|
||||
/**
|
||||
* 回测任务创建请求
|
||||
*/
|
||||
export interface BacktestCreateRequest {
|
||||
taskName: string
|
||||
leaderId: number
|
||||
initialBalance: string
|
||||
backtestDays: number // 1-30
|
||||
// 跟单配置
|
||||
copyMode?: 'RATIO' | 'FIXED'
|
||||
copyRatio?: string
|
||||
fixedAmount?: string
|
||||
maxOrderSize?: string
|
||||
minOrderSize?: string
|
||||
maxDailyLoss?: string
|
||||
maxDailyOrders?: number
|
||||
priceTolerance?: string // 百分比
|
||||
delaySeconds?: number
|
||||
supportSell?: boolean
|
||||
minOrderDepth?: string
|
||||
maxSpread?: string
|
||||
minPrice?: string
|
||||
maxPrice?: string
|
||||
maxPositionValue?: string
|
||||
keywordFilterMode?: 'DISABLED' | 'WHITELIST' | 'BLACKLIST'
|
||||
keywords?: string[]
|
||||
maxMarketEndDate?: number | null
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务列表请求
|
||||
*/
|
||||
export interface BacktestListRequest {
|
||||
leaderId?: number
|
||||
status?: 'PENDING' | 'RUNNING' | 'COMPLETED' | 'STOPPED' | 'FAILED'
|
||||
sortBy?: 'profitAmount' | 'profitRate' | 'createdAt'
|
||||
sortOrder?: 'asc' | 'desc'
|
||||
page: number
|
||||
size: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务详情请求
|
||||
*/
|
||||
export interface BacktestDetailRequest {
|
||||
id: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测交易记录列表请求
|
||||
*/
|
||||
export interface BacktestTradeListRequest {
|
||||
taskId: number
|
||||
page: number
|
||||
size: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测进度查询请求
|
||||
*/
|
||||
export interface BacktestProgressRequest {
|
||||
id: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务停止请求
|
||||
*/
|
||||
export interface BacktestStopRequest {
|
||||
id: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务删除请求
|
||||
*/
|
||||
export interface BacktestDeleteRequest {
|
||||
id: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务列表响应
|
||||
*/
|
||||
export interface BacktestListResponse {
|
||||
list: BacktestTaskDto[]
|
||||
total: number
|
||||
page: number
|
||||
size: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务详情响应
|
||||
*/
|
||||
export interface BacktestDetailResponse {
|
||||
task: BacktestTaskDto
|
||||
config: BacktestConfigDto
|
||||
statistics: BacktestStatisticsDto
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测交易记录列表响应
|
||||
*/
|
||||
export interface BacktestTradeListResponse {
|
||||
list: BacktestTradeDto[]
|
||||
total: number
|
||||
page: number
|
||||
size: number
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测进度响应
|
||||
*/
|
||||
export interface BacktestProgressResponse {
|
||||
progress: number // 0-100
|
||||
currentBalance: string
|
||||
totalTrades: number
|
||||
status: 'PENDING' | 'RUNNING' | 'COMPLETED' | 'STOPPED' | 'FAILED'
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测任务 DTO
|
||||
*/
|
||||
export interface BacktestTaskDto {
|
||||
id: number
|
||||
taskName: string
|
||||
leaderId: number
|
||||
leaderName: string | null
|
||||
leaderAddress: string | null
|
||||
initialBalance: string
|
||||
finalBalance: string | null
|
||||
profitAmount: string | null
|
||||
profitRate: string | null // 百分比
|
||||
backtestDays: number
|
||||
startTime: number
|
||||
endTime: number | null
|
||||
status: 'PENDING' | 'RUNNING' | 'COMPLETED' | 'STOPPED' | 'FAILED'
|
||||
progress: number // 0-100
|
||||
totalTrades: number
|
||||
createdAt: number
|
||||
executionStartedAt: number | null
|
||||
executionFinishedAt: number | null
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测配置 DTO
|
||||
*/
|
||||
export interface BacktestConfigDto {
|
||||
copyMode: 'RATIO' | 'FIXED'
|
||||
copyRatio: string
|
||||
fixedAmount: string | null
|
||||
maxOrderSize: string
|
||||
minOrderSize: string
|
||||
maxDailyLoss: string
|
||||
maxDailyOrders: number
|
||||
priceTolerance: string // 百分比
|
||||
delaySeconds: number
|
||||
supportSell: boolean
|
||||
minOrderDepth: string | null
|
||||
maxSpread: string | null
|
||||
minPrice: string | null
|
||||
maxPrice: string | null
|
||||
maxPositionValue: string | null
|
||||
keywordFilterMode: 'DISABLED' | 'WHITELIST' | 'BLACKLIST' | null
|
||||
keywords: string[] | null
|
||||
maxMarketEndDate: number | null
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测统计 DTO
|
||||
*/
|
||||
export interface BacktestStatisticsDto {
|
||||
totalTrades: number // 总交易笔数
|
||||
buyTrades: number // 买入笔数
|
||||
sellTrades: number // 卖出笔数
|
||||
winTrades: number // 盈利交易笔数
|
||||
lossTrades: number // 亏损交易笔数
|
||||
winRate: string // 胜率 (百分比)
|
||||
maxProfit: string // 最大单笔盈利
|
||||
maxLoss: string // 最大单笔亏损
|
||||
maxDrawdown: string // 最大回撤
|
||||
avgHoldingTime: number | null // 平均持仓时间 (毫秒)
|
||||
}
|
||||
|
||||
/**
|
||||
* 回测交易记录 DTO
|
||||
*/
|
||||
export interface BacktestTradeDto {
|
||||
id: number
|
||||
tradeTime: number
|
||||
marketId: string
|
||||
marketTitle: string | null
|
||||
side: 'BUY' | 'SELL' | 'SETTLEMENT'
|
||||
outcome: string // YES/NO 或 outcomeIndex
|
||||
outcomeIndex: number | null
|
||||
quantity: string
|
||||
price: string
|
||||
amount: string
|
||||
fee: string
|
||||
profitLoss: string | null // 仅卖出和结算时有值
|
||||
balanceAfter: string
|
||||
leaderTradeId: string | null
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user