summaryrefslogtreecommitdiff
path: root/services/backtester
diff options
context:
space:
mode:
Diffstat (limited to 'services/backtester')
-rw-r--r--services/backtester/src/backtester/config.py2
-rw-r--r--services/backtester/tests/test_engine.py4
-rw-r--r--services/backtester/tests/test_metrics.py14
-rw-r--r--services/backtester/tests/test_reporter.py6
-rw-r--r--services/backtester/tests/test_simulator.py40
-rw-r--r--services/backtester/tests/test_walk_forward.py2
6 files changed, 34 insertions, 34 deletions
diff --git a/services/backtester/src/backtester/config.py b/services/backtester/src/backtester/config.py
index f7897da..57ee1fb 100644
--- a/services/backtester/src/backtester/config.py
+++ b/services/backtester/src/backtester/config.py
@@ -5,7 +5,7 @@ from shared.config import Settings
class BacktestConfig(Settings):
backtest_initial_balance: float = 10000.0
- symbol: str = "BTCUSDT"
+ symbol: str = "AAPL"
timeframe: str = "1h"
strategy_name: str = "rsi_strategy"
candle_limit: int = 500
diff --git a/services/backtester/tests/test_engine.py b/services/backtester/tests/test_engine.py
index 743a43b..4794e63 100644
--- a/services/backtester/tests/test_engine.py
+++ b/services/backtester/tests/test_engine.py
@@ -23,14 +23,14 @@ def make_candle(symbol: str, price: float, timeframe: str = "1h") -> Candle:
)
-def make_candles(prices: list[float], symbol: str = "BTCUSDT") -> list[Candle]:
+def make_candles(prices: list[float], symbol: str = "AAPL") -> list[Candle]:
return [make_candle(symbol, p) for p in prices]
def make_signal(side: OrderSide, price: str, quantity: str = "0.1") -> Signal:
return Signal(
strategy="test",
- symbol="BTCUSDT",
+ symbol="AAPL",
side=side,
price=Decimal(price),
quantity=Decimal(quantity),
diff --git a/services/backtester/tests/test_metrics.py b/services/backtester/tests/test_metrics.py
index 582309a..55f5b6c 100644
--- a/services/backtester/tests/test_metrics.py
+++ b/services/backtester/tests/test_metrics.py
@@ -12,7 +12,7 @@ from backtester.metrics import TradeRecord, compute_detailed_metrics
def _make_trade(side: str, price: str, minutes_offset: int = 0) -> TradeRecord:
return TradeRecord(
time=datetime(2025, 1, 1, tzinfo=timezone.utc) + timedelta(minutes=minutes_offset),
- symbol="BTCUSDT",
+ symbol="AAPL",
side=side,
price=Decimal(price),
quantity=Decimal("1"),
@@ -127,39 +127,39 @@ def test_risk_free_rate_affects_sharpe():
base = datetime(2025, 1, 1, tzinfo=timezone.utc)
trades = [
TradeRecord(
- time=base, symbol="BTCUSDT", side="BUY", price=Decimal("100"), quantity=Decimal("1")
+ time=base, symbol="AAPL", side="BUY", price=Decimal("100"), quantity=Decimal("1")
),
TradeRecord(
time=base + timedelta(days=1),
- symbol="BTCUSDT",
+ symbol="AAPL",
side="SELL",
price=Decimal("110"),
quantity=Decimal("1"),
),
TradeRecord(
time=base + timedelta(days=2),
- symbol="BTCUSDT",
+ symbol="AAPL",
side="BUY",
price=Decimal("105"),
quantity=Decimal("1"),
),
TradeRecord(
time=base + timedelta(days=3),
- symbol="BTCUSDT",
+ symbol="AAPL",
side="SELL",
price=Decimal("115"),
quantity=Decimal("1"),
),
TradeRecord(
time=base + timedelta(days=4),
- symbol="BTCUSDT",
+ symbol="AAPL",
side="BUY",
price=Decimal("110"),
quantity=Decimal("1"),
),
TradeRecord(
time=base + timedelta(days=5),
- symbol="BTCUSDT",
+ symbol="AAPL",
side="SELL",
price=Decimal("108"),
quantity=Decimal("1"),
diff --git a/services/backtester/tests/test_reporter.py b/services/backtester/tests/test_reporter.py
index 2ea49c0..5199b68 100644
--- a/services/backtester/tests/test_reporter.py
+++ b/services/backtester/tests/test_reporter.py
@@ -32,7 +32,7 @@ def _make_result(with_detailed: bool = False) -> BacktestResult:
)
return BacktestResult(
strategy_name="sma_crossover",
- symbol="BTCUSDT",
+ symbol="AAPL",
total_trades=10,
initial_balance=Decimal("10000"),
final_balance=Decimal("11500"),
@@ -48,7 +48,7 @@ def test_format_report_contains_key_metrics():
report = format_report(result)
assert "sma_crossover" in report
- assert "BTCUSDT" in report
+ assert "AAPL" in report
assert "10000" in report
assert "11500" in report
assert "1500" in report
@@ -89,7 +89,7 @@ def test_export_json():
data = json.loads(json_output)
assert data["strategy_name"] == "sma_crossover"
- assert data["symbol"] == "BTCUSDT"
+ assert data["symbol"] == "AAPL"
assert "detailed" in data
assert data["detailed"]["sharpe_ratio"] == 1.5
assert data["detailed"]["monthly_returns"]["2025-01"] == 500.0
diff --git a/services/backtester/tests/test_simulator.py b/services/backtester/tests/test_simulator.py
index a407c21..62e2cdb 100644
--- a/services/backtester/tests/test_simulator.py
+++ b/services/backtester/tests/test_simulator.py
@@ -36,20 +36,20 @@ def test_simulator_initial_balance():
def test_simulator_buy_reduces_balance():
sim = OrderSimulator(Decimal("10000"))
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
result = sim.execute(signal)
assert result is True
assert sim.balance == Decimal("5000")
- assert sim.positions["BTCUSDT"] == Decimal("0.1")
+ assert sim.positions["AAPL"] == Decimal("0.1")
def test_simulator_sell_increases_balance():
sim = OrderSimulator(Decimal("10000"))
- buy_signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ buy_signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(buy_signal)
balance_after_buy = sim.balance
- sell_signal = make_signal("BTCUSDT", OrderSide.SELL, "55000", "0.1")
+ sell_signal = make_signal("AAPL", OrderSide.SELL, "55000", "0.1")
result = sim.execute(sell_signal)
assert result is True
assert sim.balance > balance_after_buy
@@ -59,20 +59,20 @@ def test_simulator_sell_increases_balance():
def test_simulator_reject_buy_insufficient_balance():
sim = OrderSimulator(Decimal("100"))
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
result = sim.execute(signal)
assert result is False
assert sim.balance == Decimal("100")
- assert sim.positions.get("BTCUSDT", Decimal("0")) == Decimal("0")
+ assert sim.positions.get("AAPL", Decimal("0")) == Decimal("0")
def test_simulator_trade_history():
sim = OrderSimulator(Decimal("10000"))
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(signal)
assert len(sim.trades) == 1
trade = sim.trades[0]
- assert trade.symbol == "BTCUSDT"
+ assert trade.symbol == "AAPL"
assert trade.side == OrderSide.BUY
assert trade.price == Decimal("50000")
assert trade.quantity == Decimal("0.1")
@@ -86,7 +86,7 @@ def test_simulator_trade_history():
def test_slippage_on_buy():
"""Buy price should increase by slippage_pct."""
sim = OrderSimulator(Decimal("100000"), slippage_pct=0.01) # 1%
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(signal)
trade = sim.trades[0]
expected_price = Decimal("50000") * Decimal("1.01") # 50500
@@ -97,10 +97,10 @@ def test_slippage_on_sell():
"""Sell price should decrease by slippage_pct."""
sim = OrderSimulator(Decimal("100000"), slippage_pct=0.01)
# Buy first (no slippage check here, just need a position)
- buy = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ buy = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(buy)
# Sell
- sell = make_signal("BTCUSDT", OrderSide.SELL, "50000", "0.1")
+ sell = make_signal("AAPL", OrderSide.SELL, "50000", "0.1")
sim.execute(sell)
trade = sim.trades[1]
expected_price = Decimal("50000") * Decimal("0.99") # 49500
@@ -116,7 +116,7 @@ def test_fee_deducted_from_balance():
"""Fees should reduce balance beyond the raw cost."""
fee_pct = 0.001 # 0.1%
sim = OrderSimulator(Decimal("100000"), taker_fee_pct=fee_pct)
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(signal)
# cost = 50000 * 0.1 = 5000, fee = 5000 * 0.001 = 5
expected_balance = Decimal("100000") - Decimal("5000") - Decimal("5")
@@ -132,7 +132,7 @@ def test_fee_deducted_from_balance():
def test_stop_loss_triggers():
"""Long position auto-closed when candle_low <= stop_loss."""
sim = OrderSimulator(Decimal("100000"))
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(signal, stop_loss=Decimal("48000"))
ts = datetime(2025, 1, 1, tzinfo=timezone.utc)
@@ -150,7 +150,7 @@ def test_stop_loss_triggers():
def test_take_profit_triggers():
"""Long position auto-closed when candle_high >= take_profit."""
sim = OrderSimulator(Decimal("100000"))
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(signal, take_profit=Decimal("55000"))
ts = datetime(2025, 1, 1, tzinfo=timezone.utc)
@@ -168,7 +168,7 @@ def test_take_profit_triggers():
def test_stop_not_triggered_within_range():
"""No auto-close when price stays within stop/tp range."""
sim = OrderSimulator(Decimal("100000"))
- signal = make_signal("BTCUSDT", OrderSide.BUY, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.BUY, "50000", "0.1")
sim.execute(signal, stop_loss=Decimal("48000"), take_profit=Decimal("55000"))
ts = datetime(2025, 1, 1, tzinfo=timezone.utc)
@@ -189,10 +189,10 @@ def test_stop_not_triggered_within_range():
def test_short_sell_allowed():
"""Can open short position with allow_short=True."""
sim = OrderSimulator(Decimal("100000"), allow_short=True)
- signal = make_signal("BTCUSDT", OrderSide.SELL, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.SELL, "50000", "0.1")
result = sim.execute(signal)
assert result is True
- assert sim.positions["BTCUSDT"] == Decimal("-0.1")
+ assert sim.positions["AAPL"] == Decimal("-0.1")
assert len(sim.open_positions) == 1
assert sim.open_positions[0].side == OrderSide.SELL
@@ -200,16 +200,16 @@ def test_short_sell_allowed():
def test_short_sell_rejected():
"""Short rejected when allow_short=False (default)."""
sim = OrderSimulator(Decimal("100000"), allow_short=False)
- signal = make_signal("BTCUSDT", OrderSide.SELL, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.SELL, "50000", "0.1")
result = sim.execute(signal)
assert result is False
- assert sim.positions.get("BTCUSDT", Decimal("0")) == Decimal("0")
+ assert sim.positions.get("AAPL", Decimal("0")) == Decimal("0")
def test_short_stop_loss():
"""Short position stop-loss triggers on candle high >= stop_loss."""
sim = OrderSimulator(Decimal("100000"), allow_short=True)
- signal = make_signal("BTCUSDT", OrderSide.SELL, "50000", "0.1")
+ signal = make_signal("AAPL", OrderSide.SELL, "50000", "0.1")
sim.execute(signal, stop_loss=Decimal("52000"))
ts = datetime(2025, 1, 1, tzinfo=timezone.utc)
diff --git a/services/backtester/tests/test_walk_forward.py b/services/backtester/tests/test_walk_forward.py
index 5ab2e7b..96abb6e 100644
--- a/services/backtester/tests/test_walk_forward.py
+++ b/services/backtester/tests/test_walk_forward.py
@@ -21,7 +21,7 @@ def _generate_candles(n=100, base_price=100.0):
price = base_price + (i % 20) - 10
candles.append(
Candle(
- symbol="BTCUSDT",
+ symbol="AAPL",
timeframe="1h",
open_time=datetime(2025, 1, 1, tzinfo=timezone.utc) + timedelta(hours=i),
open=Decimal(str(price)),