Browse Source

trading strategy

main
strange 10 months ago
parent
commit
96f12873d4
  1. 4
      config/exchange.toml
  2. 2
      internal/trading/trading_plan.go
  3. 13
      internal/trading/trading_service.go
  4. 2
      pkg/backtrace/backtrace.go
  5. 2
      pkg/data/entity/trade_plan.go
  6. 5
      pkg/strategy/buy_strategy.go
  7. 13
      pkg/strategy/exit_strategy.go
  8. 4
      pkg/strategy/gold_x.go
  9. 24
      pkg/strategy/sig_strategy.go
  10. 6
      pkg/strategy/strategy_multi_interval.go

4
config/exchange.toml

@ -18,8 +18,8 @@ receiveBuffer = 4096
marketSubscribeLimit = 16
consumeBatch = 1024
consumeLater = 2000 # 时间到达later或者数据累计到batch触发consume
httpProxy = "http://192.168.1.5:7890"
# httpProxy = "http://10.255.183.209:7890"
# httpProxy = "http://192.168.1.5:7890"
httpProxy = "http://10.255.183.209:7890"
# 模拟盘API交易地址如下:
# REST:https://www.okx.com

2
internal/trading/trading_plan.go

@ -15,7 +15,7 @@ type TradingPlan struct {
StrategyName string `json:"strategyName"`
}
func NewTradingPlan(plan entity.TradingPlan, strategy strategy.IStrategy) *TradingPlan {
func NewTradingPlan(plan entity.TradingPlan, strategy strategy.ISigStrategy) *TradingPlan {
return &TradingPlan{}
}

13
internal/trading/trading_service.go

@ -15,8 +15,8 @@ type TradingService struct {
exchangeClient pb.ExchangeServiceClient
klineStore *KlineStore
windowIndicators *collect.SyncMap[string, indicator.IWindowIndicator]
strategies *collect.SyncMap[string, strategy.IStrategy]
indicatorsW *collect.SyncMap[string, indicator.IWindowIndicator] // 注册窗口指标
strategies *collect.SyncMap[string, strategy.ISigStrategy] // 注册信号策略
publisher publish.Publisher[int64, *TradingPlan]
tradingPlan chan *TradingPlan
}
@ -29,7 +29,8 @@ func NewTradingService(
marketClientAside: marketClientAside,
exchangeClient: exchangeClient,
klineStore: NewKlineSeriesStore(exchangeClient),
windowIndicators: collect.NewSyncMap[string, indicator.IWindowIndicator](),
indicatorsW: collect.NewSyncMap[string, indicator.IWindowIndicator](),
strategies: collect.NewSyncMap[string, strategy.ISigStrategy](),
}
}
@ -55,7 +56,7 @@ func (svr *TradingService) Init() (err error) {
// RegisterWindowIndicator
func (svr *TradingService) RegisterWindowIndicator(ind indicator.IWindowIndicator) (err error) {
indName := ind.Name()
_, loaded := svr.windowIndicators.LoadOrStore(indName, ind)
_, loaded := svr.indicatorsW.LoadOrStore(indName, ind)
if loaded {
err = fmt.Errorf("window indicator name %s already duplicated", indName)
return
@ -70,7 +71,7 @@ func (svr *TradingService) MustRegisterWindowIndicator(ind indicator.IWindowIndi
}
// RegisterStrategy
func (svr *TradingService) RegisterStrategy(strategy strategy.IStrategy) (err error) {
func (svr *TradingService) RegisterStrategy(strategy strategy.ISigStrategy) (err error) {
strategyName := strategy.Meta().Name
_, loaded := svr.strategies.LoadOrStore(strategyName, strategy)
if loaded {
@ -80,7 +81,7 @@ func (svr *TradingService) RegisterStrategy(strategy strategy.IStrategy) (err er
return
}
func (svr *TradingService) MustRegisterStrategy(strategy strategy.IStrategy) {
func (svr *TradingService) MustRegisterStrategy(strategy strategy.ISigStrategy) {
if err := svr.RegisterStrategy(strategy); err != nil {
panic(err)
}

2
pkg/backtrace/backtrace.go

@ -4,7 +4,7 @@ import "sig-pub/pkg/strategy"
// 回测引擎
type BacktraceEngine struct {
strategy strategy.IStrategy
strategy strategy.ISigStrategy
}
// 多周期策略回测引擎

2
pkg/data/entity/trade_plan.go

@ -11,7 +11,7 @@ type TradingPlan struct {
Exchange pb.ExchangeType `gorm:"column:exchange" json:"exchange"` // 交易所
InstId string `gorm:"column:instId" json:"instId"` // 交易产品
Interval types.Interval `gorm:"column:interval" json:"interval"` // 交易周期
StrategyName string `gorm:"column:strategy_name" json:"strategyName"` // 策略名称
Strategy string `gorm:"column:strategy" json:"strategy"` // 策略名称
UpdateBy string `gorm:"column:update_by" json:"updateBy"` // 更新人
UpdateTime int64 `gorm:"column:update_time" json:"updateTime"` // 更新时间戳毫秒
}

5
pkg/strategy/buy_strategy.go

@ -0,0 +1,5 @@
package strategy
// TradeStrategy 下单买入策略接口(控制滑点, 仓位管理)
type TradeStrategy interface {
}

13
pkg/strategy/exit_strategy.go

@ -0,0 +1,13 @@
package strategy
import "github.com/govalues/decimal"
// todo Exit 止盈止损策略(trading service 管理)
type IExitStrategy interface {
Name() string // 获取策略名称,便于日志
Tick(ctx IExitStrategyContext)
}
type IExitStrategyContext interface {
LastPrice() decimal.Decimal
}

4
pkg/strategy/gold_x.go

@ -4,7 +4,7 @@ package strategy
type GoldX struct {
}
func (s *GoldX) New() IStrategy {
func (s *GoldX) New() ISigStrategy {
return &GoldX{}
}
@ -15,7 +15,7 @@ func (s *GoldX) Meta() StrategyMeta {
}
}
func (s *GoldX) Update(ctx IStrategyContext) {
func (s *GoldX) Update(ctx ISigStrategyContext) {
sma14 := ctx.IndicatorW("sma", 14)
sma28 := ctx.IndicatorW("sma", 28)
// 包装方法

24
pkg/strategy/strategy.go → pkg/strategy/sig_strategy.go

@ -10,16 +10,16 @@ import (
"strings"
)
// todo Exit 止盈止损策略(trading service 管理)
type IStrategy interface {
New() IStrategy
// ISigStrategy 交易信号策略接口
type ISigStrategy interface {
New() ISigStrategy
Meta() StrategyMeta
Update(ctx IStrategyContext)
Update(ctx ISigStrategyContext)
}
// todo Meta 策略调参, 回测引擎自动调参回测(最佳参数) argGenerator.next() (arg, ok)
type IStrategyAdjustable interface {
IStrategy
type ISigStrategyAdjustable interface {
ISigStrategy
NextParams() map[string]any // 根据当前策略参数, 返回下一批策略参数(并行回测 stateless)
AdjustParams(map[string]any) // 重置策略设置策略参数
}
@ -30,9 +30,9 @@ type StrategyMeta struct {
Desc string
}
// IStrategyContext 策略外部访问能力
// ISigStrategyContext 策略外部访问能力
// klineSeries, Indicator
type IStrategyContext interface {
type ISigStrategyContext interface {
Buy() // 发出多信号
Sell() // 发出空信号
@ -45,11 +45,11 @@ type IStrategyContext interface {
}
// DriverIntervalKey 生成周期驱动事件key
// interval/okx/BTC_USDT/1m,3m,5m
func DriverIntervalKey(exchangeType pb.ExchangeType, instId string, intervals ...types.Interval) string {
// interval/BTC_USDT/OKX,BINANCE/1m,3m,5m
func DriverIntervalKey(instId string, intervals []types.Interval, exchanges ...pb.ExchangeType) string {
types.IntervalsSort(intervals)
strIntervals := collect.Mapping(intervals, func(_ int, interval types.Interval) string { return string(interval) })
pubKey := fmt.Sprintf("/interval/%s/%s/%s", exchangeType.String(), instId, strings.Join(strIntervals, ","))
strExchanges := collect.Mapping(exchanges, func(_ int, exchange pb.ExchangeType) string { return exchange.String() })
pubKey := fmt.Sprintf("/interval/%s/%s/%s", instId, strings.Join(strExchanges, ","), strings.Join(strIntervals, ","))
return pubKey
}

6
pkg/strategy/strategy_multi_interval.go

@ -4,15 +4,15 @@ import "sig-pub/pkg/types"
// 多k线周期策略
type MultiIntervalStrategy interface {
IStrategy
ISigStrategy
DriverInterval() types.Interval // 驱动k线周期, 当驱动周期k线更新时则判断调用Update方法
SubscribeIntervals() []types.Interval // 订阅k线周期, 当同一时间的订阅周期都更新时调用Update方法
}
type MultiExchangeStrategy interface {
IStrategy
ISigStrategy
}
type MultiIntervalExchangeStrategy interface {
IStrategy
ISigStrategy
}

Loading…
Cancel
Save