- Implemented portfolio engine with risk-based allocation (50/50) - Added equity-based metrics for system-level evaluation - Validated portfolio against standalone strategies - Reduced max drawdown and volatility at system level - Quantitative decision closed before paper trading phase
74 lines
1.6 KiB
Python
74 lines
1.6 KiB
Python
# src/risk/stops/test_atr_stop.py
|
|
import sys
|
|
from pathlib import Path
|
|
import pandas as pd
|
|
import numpy as np
|
|
import pytest
|
|
|
|
# Añadir raíz del proyecto al path
|
|
sys.path.insert(0, str(Path(__file__).parent.parent.parent.parent))
|
|
|
|
from src.risk.stops.base import StopLoss
|
|
from src.core.trade import TradeType
|
|
from src.risk.stops.atr_stop import ATRStop
|
|
from src.core.trade import TradeType
|
|
|
|
|
|
def atr_data():
|
|
return pd.DataFrame(
|
|
{
|
|
"high": [10, 11, 12, 13, 14],
|
|
"low": [9, 10, 11, 12, 13],
|
|
"close": [9.5, 10.5, 11.5, 12.5, 13.5],
|
|
},
|
|
index=pd.date_range("2024-01-01", periods=5, freq="D"),
|
|
)
|
|
|
|
|
|
def test_atr_stop_long():
|
|
stop = ATRStop(atr_period=3, multiplier=2.0)
|
|
|
|
price = stop.get_stop_price(
|
|
data=atr_data(),
|
|
idx=4,
|
|
entry_price=14,
|
|
trade_type=TradeType.LONG,
|
|
)
|
|
|
|
assert price < 14 # stop por debajo
|
|
|
|
|
|
def test_atr_stop_short():
|
|
stop = ATRStop(atr_period=3, multiplier=2.0)
|
|
|
|
price = stop.get_stop_price(
|
|
data=atr_data(),
|
|
idx=4,
|
|
entry_price=14,
|
|
trade_type=TradeType.SHORT,
|
|
)
|
|
|
|
assert price > 14 # stop por encima
|
|
|
|
|
|
def test_atr_stop_requires_columns():
|
|
stop = ATRStop()
|
|
|
|
bad_data = pd.DataFrame({"close": [1, 2, 3]})
|
|
|
|
with pytest.raises(ValueError):
|
|
stop.get_stop_price(
|
|
data=bad_data,
|
|
idx=2,
|
|
entry_price=3,
|
|
trade_type=TradeType.LONG,
|
|
)
|
|
|
|
|
|
def test_atr_stop_invalid_params():
|
|
with pytest.raises(ValueError):
|
|
ATRStop(atr_period=0)
|
|
|
|
with pytest.raises(ValueError):
|
|
ATRStop(multiplier=0)
|