Daily UpCap+MomGap trading on an IBKR paper account
Connects to IB Gateway through ib_async and trades the S&P 500 with the UpCap+MomGap factor combo ported from quant-trading's fc_up_cap_mom_gap_daily: signal on opens through today's open, equal weight top 10, MOC orders filled at today's close, 10% resize band. - make universe/bars/check/plan/submit/fills for the daily loop; refuses non-paper accounts unless allow_live, open orders, stale bars, and orders outside 09:31-15:45 ET - make backtest replays the live loop day by day with plan_orders and IBKR Fixed commissions; selection uses each day's index members - make bars fails fast when the Gateway's historical farm is down Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
43
tests/test_rebalance.py
Normal file
43
tests/test_rebalance.py
Normal file
@@ -0,0 +1,43 @@
|
||||
import pytest
|
||||
|
||||
from ibkr_quant.rebalance import plan_orders
|
||||
|
||||
|
||||
def test_closes_dropped_names_and_sells_before_buys():
|
||||
orders = plan_orders(
|
||||
target_weights={"AAPL": 0.5, "MSFT": 0.5},
|
||||
positions={"AAPL": 10, "NVDA": 7},
|
||||
prices={"AAPL": 100.0, "MSFT": 300.0, "NVDA": 50.0},
|
||||
investable=10_000,
|
||||
min_trade_value=200,
|
||||
)
|
||||
assert [(o.symbol, o.delta) for o in orders] == [("NVDA", -7), ("AAPL", 40), ("MSFT", 16)]
|
||||
|
||||
|
||||
def test_skips_small_adjustments_but_not_full_exits():
|
||||
orders = plan_orders(
|
||||
target_weights={"AAPL": 1.0},
|
||||
positions={"AAPL": 99, "KO": 1},
|
||||
prices={"AAPL": 100.0, "KO": 60.0},
|
||||
investable=10_000,
|
||||
min_trade_value=200,
|
||||
)
|
||||
assert [(o.symbol, o.delta) for o in orders] == [("KO", -1)]
|
||||
|
||||
|
||||
def test_refuses_to_plan_without_prices():
|
||||
with pytest.raises(ValueError, match="NVDA"):
|
||||
plan_orders({"AAPL": 1.0}, {"NVDA": 5}, {"AAPL": 100.0}, 10_000, 0)
|
||||
|
||||
|
||||
def test_resize_band_keeps_near_target_holdings():
|
||||
orders = plan_orders(
|
||||
target_weights={"AAPL": 0.5, "MSFT": 0.5},
|
||||
positions={"AAPL": 46, "MSFT": 10},
|
||||
prices={"AAPL": 100.0, "MSFT": 300.0},
|
||||
investable=10_000,
|
||||
min_trade_value=50,
|
||||
resize_band=0.10,
|
||||
)
|
||||
# AAPL is 8% under target and stays; MSFT is 40% under and tops up.
|
||||
assert [(o.symbol, o.delta) for o in orders] == [("MSFT", 6)]
|
||||
Reference in New Issue
Block a user