src/tzutrader/strategy

Strategy module for tzutrader

This module provides a framework for creating and using trading strategies. It includes a base Strategy class and several pre-built strategies.

Features:

  • Base Strategy class with common interface
  • Pre-built strategies (RSI, MA Crossover, MACD, Bollinger Bands)
  • Easy custom strategy creation
  • Batch and streaming modes
  • Signal generation for Buy/Sell/Stay decisions

Types

BollingerStrategy = ref object of Strategy
  period*: int
  stdDev*: float64
  lastPosition*: Position
Bollinger Bands mean reversion strategy Buy when price touches lower band, sell when price touches upper band
CrossoverStrategy = ref object of Strategy
  fastPeriod*: int
  slowPeriod*: int
  fastMA*: SMA
  slowMA*: SMA
  lastFastAbove*: bool
Moving average crossover strategy Golden cross (fast > slow) = buy, Death cross (fast < slow) = sell
MACDStrategy = ref object of Strategy
  fastPeriod*: int
  slowPeriod*: int
  signalPeriod*: int
  macdIndicator*: MACD
  lastMACDAbove*: bool
MACD-based strategy Bullish when MACD > signal, bearish when MACD < signal
RSIStrategy = ref object of Strategy
  period*: int
  oversold*: float64
  overbought*: float64
  rsiIndicator*: RSI
  lastSignal*: Position
RSI-based strategy Buys when RSI is oversold, sells when overbought
Strategy = ref object of RootObj
  name*: string
  symbol*: string
  history*: seq[OHLCV]       ## For strategies that need bar history
Base strategy class All strategies should inherit from this

Procs

proc newBollingerStrategy(period: int = 20; stdDev: float64 = 2.0;
                          symbol: string = ""): BollingerStrategy {....raises: [],
    tags: [], forbids: [].}

Create a new Bollinger Bands strategy

Args: period: BB period (default 20) stdDev: Number of standard deviations (default 2.0) symbol: Symbol to trade (optional)

Returns: New Bollinger Bands strategy instance

proc newCrossoverStrategy(fastPeriod: int = 50; slowPeriod: int = 200;
                          symbol: string = ""): CrossoverStrategy {....raises: [],
    tags: [], forbids: [].}

Create a new MA crossover strategy

Args: fastPeriod: Fast moving average period (default 50) slowPeriod: Slow moving average period (default 200) symbol: Symbol to trade (optional)

Returns: New crossover strategy instance

proc newMACDStrategy(fastPeriod: int = 12; slowPeriod: int = 26;
                     signalPeriod: int = 9; symbol: string = ""): MACDStrategy {.
    ...raises: [], tags: [], forbids: [].}

Create a new MACD strategy

Args: fastPeriod: Fast EMA period (default 12) slowPeriod: Slow EMA period (default 26) signalPeriod: Signal line EMA period (default 9) symbol: Symbol to trade (optional)

Returns: New MACD strategy instance

proc newRSIStrategy(period: int = 14; oversold: float64 = 30.0;
                    overbought: float64 = 70.0; symbol: string = ""): RSIStrategy {.
    ...raises: [], tags: [], forbids: [].}

Create a new RSI strategy

Args: period: RSI period (default 14) oversold: Oversold threshold for buy signals (default 30) overbought: Overbought threshold for sell signals (default 70) symbol: Symbol to trade (optional)

Returns: New RSI strategy instance

Methods

method analyze(s: BollingerStrategy; data: seq[OHLCV]): seq[Signal] {.
    ...raises: [], tags: [], forbids: [].}
Analyze data using Bollinger Bands, generating a signal for each bar
method analyze(s: CrossoverStrategy; data: seq[OHLCV]): seq[Signal] {.
    ...raises: [], tags: [], forbids: [].}
Analyze data using MA crossover, generating a signal for each bar
method analyze(s: MACDStrategy; data: seq[OHLCV]): seq[Signal] {....raises: [],
    tags: [], forbids: [].}
Analyze data using MACD, generating a signal for each bar
method analyze(s: RSIStrategy; data: seq[OHLCV]): seq[Signal] {....raises: [],
    tags: [], forbids: [].}
Analyze data using RSI, generating a signal for each bar
method analyze(s: Strategy; data: seq[OHLCV]): seq[Signal] {.base,
    ...raises: [StrategyError], tags: [], forbids: [].}

Analyze historical data and generate signals for each bar (batch mode)

Args: data: Historical OHLCV data

Returns: Sequence of signals, one for each bar

method name(s: Strategy): string {.base, ...raises: [], tags: [], forbids: [].}
Get strategy name
method onBar(s: BollingerStrategy; bar: OHLCV): Signal {....raises: [], tags: [],
    forbids: [].}
Bollinger Bands strategy doesn't have a good streaming implementation because it needs full history for standard deviation calculation. We'll just delegate to analyze with a single bar.
method onBar(s: CrossoverStrategy; bar: OHLCV): Signal {....raises: [], tags: [],
    forbids: [].}
Process single bar using streaming MAs
method onBar(s: MACDStrategy; bar: OHLCV): Signal {....raises: [], tags: [],
    forbids: [].}
Process single bar using streaming MACD
method onBar(s: RSIStrategy; bar: OHLCV): Signal {....raises: [], tags: [],
    forbids: [].}
Process single bar using streaming RSI
method onBar(s: Strategy; bar: OHLCV): Signal {.base, ...raises: [StrategyError],
    tags: [], forbids: [].}

Process a single bar and generate signal (streaming mode)

Args: bar: Single OHLCV bar

Returns: Signal with position recommendation

method reset(s: BollingerStrategy) {....raises: [], tags: [], forbids: [].}
Reset Bollinger strategy state
method reset(s: CrossoverStrategy) {....raises: [], tags: [], forbids: [].}
Reset crossover strategy state
method reset(s: MACDStrategy) {....raises: [], tags: [], forbids: [].}
Reset MACD strategy state
method reset(s: RSIStrategy) {....raises: [], tags: [], forbids: [].}
Reset RSI strategy state
method reset(s: Strategy) {.base, ...raises: [], tags: [], forbids: [].}
Reset strategy state (for streaming mode)