package sentio import ( "time" ) type Strategy interface { Name() string Model() string MarketId() string PositionSymbols() map[Side]string PositionProbabilities() map[Side]float64 Interval() uint8 Cooldown(periods uint8) time.Duration Handle(market Market, probability Probability) error } //type BaseStrategy struct { // Strategy //} // //func (strategy BaseStrategy) Symbols() []string { // var symbols []string // // for side, s := range strategy.PositionSymbols() { // if BASE == side { // continue // } // // symbols = append(symbols, s) // } // // return symbols //} // //func (strategy BaseStrategy) CloseAllOrders(market Market) error { // var ( // symbols = strategy.Symbols() // orders []Order // err error // ) // // if orders, err = market.Orders(OrderListCriteria{ // Status: "open", // Symbols: symbols, // Nested: true, // }); err != nil { // return err // } // // for i := range orders { // if _, err = market.CloseOrder(orders[i].GetId()); err != nil { // return err // } // } // // return nil //} // //func (strategy BaseStrategy) AtrStopLoss(market Market, symbols ...string) (map[string]float64, error) { // var ( // stoplosses map[string]float64 // bars map[string][]Bar // err error // ) // // if bars, err = market.HistoricalBars(symbols, time.Minute, nil); err != nil { // return nil, err // } // // if bars == nil || len(bars) < ATR_PERIOD { // return nil, errors.New("AtrStopLoss: could not calculate stoploss for too short timeseries") // } // // stoplosses = make(map[string]float64) // for s := range bars { // h := make([]float64, len(bars[s])) // l := make([]float64, len(bars[s])) // c := make([]float64, len(bars[s])) // // for i := range bars[s] { // h[i] = bars[s][i].High // l[i] = bars[s][i].Low // c[i] = bars[s][i].Close // } // // trailing := indicator.AtrTrailingStopLoss(h, l, c, ATR_PERIOD, ATR_MULTIPLIER, ATR_HHV) // stoplosses[s] = trailing[len(trailing)-1] // } // // return stoplosses, nil //} // //func (strategy BaseStrategy) CreateOrder(m Market, t Side, proba Probability, p Portfolio, q map[string]Quote, sl map[string]float64) error { // var ( // symbol = strategy.PositionSymbols()[t] // position Position // account MarketAccount // has = false // threshold float64 // size uint // ok bool // err error // ) // // // ensure portfolio // position, has = p.Get(symbol) // // // define threshold // if threshold, ok = strategy.PositionProbabilities()[t]; !ok { // threshold = -1 // } // // if threshold == -1 || symbol == "" { // return nil // } // // // Prevent Market.CreateOrder when BidPrice less than ATR_STOPLOSS_THRESHOLD // if q[symbol].BidPrice/sl[symbol] < ATR_STOPLOSS_THRESHOLD { // return nil // } // // if account, err = m.Account(); err != nil { // return err // } // // if account.GetCash() < q[symbol].BidPrice { // return ErrTooSmallOrder // } // // if !has && proba.Value > threshold { // // // create a new order // if size = uint(math.Floor(account.GetCash() * .7 / q[symbol].BidPrice)); size < 1 { // return ErrTooSmallOrder // } // // _, err = m.CreateOrder(symbol, size, sl[symbol]) // return err // // } else if has && position.GetAvgPrice()/position.GetCurrentPrice() > EXTRA_POSITION_THRESHOLD { // // // create an extra position // if size = uint(math.Floor(account.GetCash() * .5 / q[symbol].BidPrice)); size < 1 { // return ErrTooSmallOrder // } // // _, err = m.CreateOrder(symbol, size, sl[symbol]) // return err // } // // return nil //}