API Reference

Complete documentation for the RLX Backtester Python API

🔑

Licensing

RLX requires a valid license key for production use. Get your license at rlxbt.com/pricing.

PlanMax BarsRLIntrabarMulti-StrategyPrice
Starter500K$29/mo
ProUnlimited$79/mo
Institutional Unlimited$499/mo

TradingEngine

The main entry point for running backtests. Manages portfolio, executes trades, and calculates metrics.

Constructor

Python
engine = rlx.TradingEngine(
    initial_capital=100000.0,      # Starting capital
    commission=0.0,                 # Commission rate (0.1 = 0.1%)
    slippage=0.0,                   # Slippage per trade
    contract_size=1.0,              # Size of one contract
    enable_dynamic_tp_sl=True,     # Enable TP/SL from signals
    exit_controller=None,          # ExitController instance
    license_key="rlx_pro_xxx"      # License key (production)
)

Methods

run_with_signals(data, signal_column="signal")

Runs backtest using pre-calculated signals in the data.

Parameters:

  • data — DataFrame with OHLCV and signal column
  • signal_column — Column name with signals (1/-1/0)

Returns:BacktestResult

execute_backtest(strategy, data)

Runs backtest using a strategy object that generates signals.

Parameters:

  • strategy — Strategy instance with generate_signals method
  • data — DataFrame or list of Bar objects

run_intrabar_backtest(strategy, main_data, intrabar_data)

High-precision backtest with intrabar resolution for accurate TP/SL.

Parameters:

  • main_data — Main timeframe data (e.g., 1H)
  • intrabar_data — Higher resolution data (e.g., 1M)

run_multi_strategy(strategies, data, strategy_names, allocation_weights)

Run multiple strategies as a portfolio.

Returns:MultiStrategyResult

ExitController

Advanced exit management beyond simple TP/SL. Supports time-based, session-based, and drawdown-based exits.

Python
from rlxbt import ExitController, ExitRules

# Create exit rules
rules = ExitRules(
    hold_bars=10,               # Close after 10 bars
    max_hold_minutes=60,        # Or after 60 minutes
    exit_at_night=True,         # Close at night
    night_start_hour=22,        # Night starts 22:00 UTC
    night_end_hour=6,           # Night ends 06:00 UTC
    max_drawdown_percent=5.0,   # Close if DD > 5%
    min_profit_percent=2.0     # Close if profit > 2%
)

# Create controller and attach to engine
controller = ExitController(rules)
engine.set_exit_controller(controller)

ExitRules

Parameter Type Description
hold_barsint? Max bars to hold position
max_hold_minutes int?Max time in minutes
exit_at_night bool? Close during night hours
night_start_hour int? Night start (UTC). Default: 22
night_end_hour int? Night end (UTC). Default: 6
max_drawdown_percent float? Force exit on drawdown %
min_profit_percent float?Force exit on profit %
custom_rules Dict[str, float]? Custom key-value rules for extension

Static Factory Methods

Python
# Simple time-based exit
rules = ExitRules.hold_bars_only(bars=10)

# Day trading preset (includes night exit and drawdown protection)
rules = ExitRules.day_trading_rules(hold_bars=50, max_hold_minutes=240)

Intrabar Resolution

Most backtesters only see OHLC values, making it impossible to know if price hit stop-loss or take-profit first. RLX solves this with intrabar analysis.

The Problem

Bar: Open=100, High=105, Low=95, Close=102
Position: Long at 100, SL=96, TP=104

Traditional Backtest

Can't determine order — High or Low first?

RLX Intrabar

Uses 1M data to determine exact sequence

Python
# Load main timeframe (signals generated here)
main_df = pd.read_csv("BTCUSDT_1h.csv")

# Load intrabar data (execution happens here)
intrabar_df = pd.read_csv("BTCUSDT_1m.csv")

# Run with intrabar precision
result = engine.run_intrabar_backtest(
    strategy=my_strategy,
    main_data=main_df,
    intrabar_data=intrabar_df
)

How It Works

  1. Strategy runs on Main Timeframe (e.g., 1 Hour) to generate signals
  2. Once a position is opened, engine switches to Intrabar Data (e.g., 1 Minute) to check for TP/SL hits
  3. This prevents "looking into the future" where High/Low of a bar might trigger both TP and SL

Data Structures

Bar

Represents a single OHLCV candle in the market data.

Python
bar = rlx.Bar(
    timestamp=1609459200,    # Unix timestamp
    open=100.0,               # Open price
    high=105.0,               # High price
    low=98.0,                 # Low price
    close=103.0,              # Close price
    volume=1000.0             # Volume
)

EnhancedSignal

A trading signal with optional Take Profit and Stop Loss levels for precise position management.

Python
signal = rlx.EnhancedSignal(
    signal=1,              # 1 = Long, -1 = Short, 0 = Flat
    take_profit=105.0,     # Optional TP price level
    stop_loss=95.0         # Optional SL price level
)
signal = 1

Long position — buy and hold

signal = -1

Short position — sell and hold

signal = 0

Flat — close any position

BacktestResult

Contains comprehensive results from a backtest simulation.

Attribute Type Description
initial_capitalfloatStarting capital
final_capitalfloatEnding portfolio value
total_returnfloatPercentage return (e.g., 0.15 for 15%)
total_tradesintNumber of completed trades
winning_tradesintNumber of profitable trades
losing_tradesintNumber of losing trades
equity_curveList[float]Portfolio value at each bar
equity_curve_timestampsList[int]Unix timestamps for equity curve
tradesList[TradeResult]Detailed history of all trades
metricsDict[str, float]Performance metrics (Sharpe, Drawdown, etc.)
trade_analysisDict[str, float]Trade statistics (avg_win, avg_loss)
total_commissionfloatTotal fees paid
drawdown_seriesList[DrawdownPoint]Drawdown at each timestamp
daily_returnsList[DailyReturn]Daily return breakdown

TradeResult

Details of a single completed trade.

Entry/Exit Info

  • entry_timeint

    Unix timestamp of entry

  • exit_timeint

    Unix timestamp of exit

  • entry_pricefloat

    Price at entry

  • exit_pricefloat

    Price at exit

  • sidestr

    "long" or "short"

P&L & Position

  • pnlfloat

    Profit/Loss in quote currency

  • returnsfloat

    Percentage return of the trade

  • quantityfloat

    Number of contracts traded

  • contract_sizefloat

    Size of one contract

  • commission_amountfloat

    Commission paid for this trade

Exit Info

  • exit_reasonExitReason

    Why the trade was closed

  • take_profitOptional[float]

    Take profit level if set

  • stop_lossOptional[float]

    Stop loss level if set

Computed Properties

  • directionint

    1 for long, -1 for short

  • profitfloat

    Alias for pnl

  • commissionfloat

    Alias for commission_amount

ExitReason

Enum representing the reason for closing a position.

None

No exit

TakeProfit

TP level hit

StopLoss

SL level hit

Signal

Strategy signal

EndOfData

Backtest finished

MaxBarsReached

Hold limit exceeded

MaxTimeReached

Time limit exceeded

NightExit

Night session

MaxDrawdown

DD limit exceeded

MinProfitReached

Profit target hit

MultiStrategyResult

Result object returned by run_multi_strategy.

Attribute Type Description
strategiesList[StrategyResult] Individual results for each strategy
portfolio_result BacktestResult Combined portfolio performance
Python
# Run multiple strategies as a portfolio
result = engine.run_multi_strategy(
    strategies=[strategy_a, strategy_b, strategy_c],
    data=market_data,
    strategy_names=["Momentum", "Mean Reversion", "Breakout"],
    allocation_weights=[0.4, 0.3, 0.3]  # Must sum to 1.0
)

# Access individual strategy results
for strat in result.strategies:
    print(f"{strat.name}: {strat.total_return:.2%}")

# Access combined portfolio
print(f"Portfolio Return: {result.portfolio_result.total_return:.2%}")

Performance Metrics

RLX calculates 30+ institutional-grade metrics. Access via result.metrics.

Basic Metrics

Metric Description
total_returnTotal percentage return over the backtest period
annual_returnAnnualized return (CAGR)
total_tradesTotal number of completed trades
winning_tradesNumber of profitable trades
losing_tradesNumber of losing trades
win_ratePercentage of winning trades
profit_factorGross profit / Gross loss
avg_winAverage profit on winning trades
avg_lossAverage loss on losing trades
largest_winLargest single winning trade
largest_lossLargest single losing trade
avg_tradeAverage P&L per trade
expectancyExpected value per trade

Accessing Metrics

Python
# From BacktestResult
result = engine.run_with_signals(data)

# Access basic metrics
print(f"Sharpe Ratio: {result.metrics['sharpe_ratio']:.2f}")
print(f"Max Drawdown: {result.metrics['max_drawdown']:.2%}")
print(f"Win Rate: {result.metrics['win_rate']:.2%}")

# From DashboardResult (more detailed)
dashboard = generator.generate_dashboard(result, data)
metrics = dashboard.performance_metrics

print(f"Sortino Ratio: {metrics.sortino_ratio:.2f}")
print(f"VaR 95%: {metrics.var_95:.2%}")
print(f"Omega Ratio: {metrics.omega_ratio:.2f}")
print(f"Kelly Criterion: {metrics.kelly_criterion:.2%}")

Reinforcement Learning

🤖

Gym-Compatible RL Environment

Train your own trading agents using popular RL libraries like Stable-Baselines3, Ray RLlib, or custom implementations. The RLEnvironment wraps the TradingEngine and handles state observation, action execution, and reward calculation.

RLEnvironment Constructor

Python
env = rlx.RLEnvironment(
    initial_capital=100000.0,    # Starting capital
    commission=0.0,               # Commission rate per trade
    slippage=0.0,                 # Slippage per trade
    window_size=20,              # Number of past bars in observation
    exit_controller=None         # Optional ExitController instance
)
Parameter Type Default Description
initial_capital float100000.0Starting capital
commissionfloat0.0Commission rate per trade
slippagefloat0.0Slippage per trade
window_sizeint20Past bars in observation
exit_controller ExitController?NoneCustom exit logic

Methods

load_data(data)

Loads historical market data into the environment.

Parameters:

  • data — A pandas DataFrame containing OHLCV data

reset()

Resets the environment to the beginning of the data or a random starting point.

Returns:

  • (observation, info) — Tuple of initial state vector and info dict

step(action)

Executes an action in the environment and advances one time step.

Parameters:

  • action (int) — The action to take (0, 1, or 2)

Returns:

  • (observation, reward, done, truncated, info)

Action Space

0

Hold / Neutral

Close position if open

1

Long

Open/flip to long

2

Short

Open/flip to short

Observation Space

The observation vector is a flattened list containing market data and account state:

Market Data Window (window_size × 5)

  • • Normalized Open price (relative to previous close)
  • • Normalized High price (relative to previous close)
  • • Normalized Low price (relative to previous close)
  • • Normalized Close price (relative to previous close)
  • • Log-normalized Volume

Account State (3 features)

  • • Normalized Portfolio Value
  • • Position Direction (1.0, 0.0, or -1.0)
  • • Position Status (1.0 if open, 0.0 if closed)

Total Dimension:(window_size × 5) + 3

Example: window_size=20 → 20×5 + 3 = 103 features

Basic Example

Python
import rlx
import pandas as pd

# Load market data
df = pd.read_csv("BTCUSDT_1h.csv")

# Create environment
env = rlx.RLEnvironment(
    initial_capital=100000.0,
    window_size=10
)
env.load_data(df)

# Training loop
obs, info = env.reset()
done = False

while not done:
    action = 1  # Example: Always go Long
    obs, reward, done, truncated, info = env.step(action)
    print(f"Reward: {reward:.2f}%, Portfolio: ${info['portfolio_value']:.2f}")

Example with Exit Rules

For proper risk management, configure exit rules through an ExitController:

Python
import rlx

# Define exit rules
rules = rlx.ExitRules(
    hold_bars=12,               # Max 12 bars in position
    max_drawdown_percent=3.0,   # Stop loss at 3% drawdown
    min_profit_percent=1.5,    # Take profit at 1.5%
)

# Create exit controller
exit_controller = rlx.ExitController(rules)

# Create environment with exit rules
env = rlx.RLEnvironment(
    initial_capital=100000.0,
    commission=0.001,            # 0.1% commission
    slippage=0.0,
    window_size=20,
    exit_controller=exit_controller
)
env.load_data(df)

Training Results with Different Exit Rules

Real benchmark (BTCUSDT 1h, PPO agent, 100K training steps):

Configuration Test Return Sharpe Max DD Trades
No Rules (baseline)-14.01%-0.048050.37%106
Conservative (2% SL)-12.14%-0.001242.90%5,914
Aggressive (5% SL) ⭐ +28.50%0.040717.84%767

💡 Key Insight

Proper exit rules dramatically improve RL agent performance by:

  • 1. Limiting downside risk with max_drawdown_percent
  • 2. Securing profits early with min_profit_percent
  • 3. Preventing overexposure with hold_bars limits

Graph Analysis

🔗

Graph-Based Trade Analysis

The GraphAnalyzer converts backtest results into a directed graph of trades, features, and patterns. This enables advanced analysis such as finding winning streaks, loss recovery patterns, and correlation clusters — just like institutional hedge funds do.

GraphAnalyzer Constructor

Python
import json

# Convert backtest result to JSON
result_json = json.dumps(result.__dict__, default=lambda o: o.__dict__)

# Create analyzer
analyzer = rlx.GraphAnalyzer(backtest_result_json=result_json)

Note: The constructor takes a JSON string representation of a BacktestResult. This allows the graph to be constructed from serialized data as well.

Methods

find_patterns(query)

Searches the graph for patterns matching a specific query language.

Parameters:

  • query (str) — Pattern definition string (e.g., "WinningStreak → WinningStreak")

Returns:

  • List[PatternMatch]

find_hedge_fund_patterns()

Automatically searches for common institutional trading patterns.

Returns:

  • List[PatternMatch]

Winning Streaks

3+ consecutive wins

Loss Recovery

Loss → larger Win

ML Signals

High confidence signals

Volatility Regime

Regime adaptation

Correlation Clusters

Related trade groups

generate_pattern_report()

Generates a human-readable text report summarizing the patterns found in the backtest.

Returns:

  • str — The report text

explain_pattern(pattern_id)

Provides a detailed, human-readable explanation of a specific pattern ID found by the analyzer.

Parameters:

  • pattern_id (str) — The ID of the pattern to explain

Returns:

  • str

export_graph()

Exports the entire graph structure (nodes and edges) to a JSON string for visualization.

Returns:

  • str — JSON string

Complete Example

Python
import rlx
import json

# Run backtest
engine = rlx.TradingEngine(initial_capital=100000)
result = engine.execute_backtest(strategy, data)

# Convert result to JSON
result_json = json.dumps(result.__dict__, default=lambda o: o.__dict__)

# Create analyzer
analyzer = rlx.GraphAnalyzer(result_json)

# Find institutional patterns
patterns = analyzer.find_hedge_fund_patterns()
print(f"Found {len(patterns)} patterns")

# Generate report
report = analyzer.generate_pattern_report()
print(report)

# Explain specific pattern
if patterns:
    explanation = analyzer.explain_pattern(patterns[0].id)
    print(explanation)

# Export for visualization
graph_json = analyzer.export_graph()
with open("trade_graph.json", "w") as f:
    f.write(graph_json)

Example Pattern Report

=== TRADE PATTERN ANALYSIS REPORT ===

📊 Backtest Summary:
   Total Trades: 156
   Win Rate: 58.3%
   Profit Factor: 1.87

🔥 Winning Streaks Detected: 12
   Longest Streak: 7 trades
   Average Streak Length: 3.2 trades
   Best Streak P&L: +$4,230.50

🔄 Loss Recovery Patterns: 8
   Recovery Rate: 87.5%
   Average Recovery P&L: +$890.25

📈 Correlation Clusters: 3
   Cluster 1: BTC momentum trades (23 trades)
   Cluster 2: Mean reversion plays (18 trades)
   Cluster 3: Breakout entries (12 trades)

💡 Key Insights:
   • Strategy performs best during high volatility
   • Average 2.3 bars between cluster trades
   • 73% of losses recovered within 3 trades
        

Dashboard & Visualization

The RLX Backtester includes a powerful built-in dashboard for visualizing backtest results, analyzing trades, and inspecting performance metrics.

DashboardGenerator

The DashboardGenerator class processes backtest results and generates data structures for visualization.

Python
generator = rlx.DashboardGenerator(
    initial_capital=100000.0,         # Starting capital
    commission=0.0,                    # Commission rate
    slippage=0.0,                      # Slippage per trade
    use_intrabar_resolution=False,   # Process intrabar data
    contract_size=1.0                 # Contract size
)

Methods

generate_dashboard(backtest_result, main_data, intrabar_data=None)

Processes raw backtest results into a structured DashboardResult.

export_to_json(dashboard_result, filename="dashboard.json")

Exports the full dashboard data to a JSON file.

plot(dashboard_result, port=8000, auto_open=True)

Launches a local web server to visualize results in an interactive dashboard.

export_trades_to_csv(extended_trades, filename="trades.csv")

Exports all trades to a CSV file with extended statistics.

DashboardResult

Contains all processed data for visualization.

Attribute Type Description
backtest_result BacktestResultOriginal backtest results
extended_trades List[ExtendedTradeInfo] Trades with additional analytics
performance_metrics PerformanceMetricsAll calculated metrics
equity_curveList[EquityPoint]Equity over time
drawdown_curve List[DrawdownPoint]Drawdown over time
monthly_returns List[MonthlyReturn]Returns by month
trade_statistics TradeStatisticsAggregated trade stats

ExtendedTradeInfo

Extended trade information with MFE/MAE and intrabar data.

Basic Info

  • trade_idint
  • open_timeint
  • close_timeint
  • entry_pricefloat
  • exit_pricefloat
  • sidestr

P&L Info

  • profitfloat
  • returnsfloat
  • exit_reasonstr
  • duration_barsint
  • price_changefloat
  • price_change_pctfloat

MFE/MAE Analysis

  • max_favorable_excursionfloat

    Maximum profit during trade (MFE)

  • max_adverse_excursionfloat

    Maximum drawdown during trade (MAE)

Intrabar Data

  • intrabar_dataList[IntrabarPoint]?
  • entry_bar_ohlcBarOHLC?
  • exit_bar_ohlcBarOHLC?
  • take_profitfloat?
  • stop_lossfloat?

Helper Structures

IntrabarPoint

High-resolution price data within a trade.

  • timestampint
  • pricefloat
  • unrealized_pnlfloat
  • price_change_from_entryfloat
  • price_change_pct_from_entryfloat

EquityPoint

Single point on the equity curve.

  • timestampint
  • equityfloat
  • returnsfloat
  • cumulative_returnsfloat

DrawdownPoint

Single point on the drawdown curve.

  • timestampint
  • drawdownfloat
  • drawdown_pctfloat
  • peak_equityfloat
  • current_equityfloat

MonthlyReturn

Monthly performance breakdown.

  • yearint
  • monthint (1-12)
  • return_pctfloat
  • trades_countint

TradeStatistics

Aggregated trade statistics.

Attribute Type Description
total_tradesintTotal trades
winning_tradesintProfitable trades
losing_tradesintLosing trades
win_ratefloatWin percentage
avg_winfloatAverage winning trade
avg_lossfloatAverage losing trade
avg_tradefloatAverage trade P&L
largest_winfloatBiggest winner
largest_lossfloatBiggest loser
max_consecutive_winsintLongest win streak
max_consecutive_lossesintLongest loss streak
avg_trade_durationfloatAverage duration (seconds)
avg_bars_in_tradefloatAverage bars per trade
expectancyfloatExpected value per trade
kelly_criterionfloatOptimal position size

Web Dashboard API

When the dashboard server is running (via plot()), it exposes a REST API for programmatic access.

Base URL:http://localhost:8000

Endpoint Description
GET /api/health Check server status and uptime
GET /api/dashboard-data Full dashboard dataset
GET /api/trades List all trades (supports filters: side, limit, offset)
GET /api/trades/:trade_id Detailed info for specific trade
GET /api/performance-metrics All calculated metrics
GET /api/equity-curve Equity curve data points
GET /api/monthly-returns Monthly return statistics
Python
import requests

response = requests.get("http://localhost:8000/api/performance-metrics")
metrics = response.json()['data']

print(f"Sharpe Ratio: {metrics['sharpe_ratio']:.2f}")
print(f"Max Drawdown: {metrics['max_drawdown']:.2%}")