Add test for MQL5 bridge
This commit is contained in:
@@ -0,0 +1,131 @@
|
||||
"""Tests for MQL5 GlobalVariable bridge."""
|
||||
|
||||
import responses
|
||||
import pytest
|
||||
|
||||
import mt5bridge_ccxt
|
||||
|
||||
|
||||
class TestMql5Bridge:
|
||||
@responses.activate
|
||||
def test_list(self, exchange_config):
|
||||
responses.add(
|
||||
responses.GET,
|
||||
"http://mock-mt5bridge:8080/gvar",
|
||||
json={"data": [
|
||||
{"name": "AT_Trend_XAUUSD", "value": 1.0},
|
||||
{"name": "AT_Buy_XAUUSD", "value": 1.0},
|
||||
], "count": 2, "format": "json"},
|
||||
status=200,
|
||||
)
|
||||
ex = mt5bridge_ccxt.mt5bridge(exchange_config)
|
||||
gvars = ex.mql5.list()
|
||||
assert len(gvars) == 2
|
||||
assert gvars[0]["name"] == "AT_Trend_XAUUSD"
|
||||
|
||||
@responses.activate
|
||||
def test_get_existing(self, exchange_config):
|
||||
responses.add(
|
||||
responses.GET,
|
||||
"http://mock-mt5bridge:8080/gvar/AT_Trend_XAUUSD",
|
||||
json={"name": "AT_Trend_XAUUSD", "value": 1.0},
|
||||
status=200,
|
||||
)
|
||||
ex = mt5bridge_ccxt.mt5bridge(exchange_config)
|
||||
assert ex.mql5.get("AT_Trend_XAUUSD") == 1.0
|
||||
|
||||
@responses.activate
|
||||
def test_get_missing_returns_default(self, exchange_config):
|
||||
responses.add(
|
||||
responses.GET,
|
||||
"http://mock-mt5bridge:8080/gvar/MISSING",
|
||||
json={"detail": "Not found"}, status=404,
|
||||
)
|
||||
ex = mt5bridge_ccxt.mt5bridge(exchange_config)
|
||||
assert ex.mql5.get("MISSING") is None
|
||||
assert ex.mql5.get("MISSING", default=42) == 42
|
||||
|
||||
@responses.activate
|
||||
def test_set(self, exchange_config):
|
||||
responses.add(
|
||||
responses.POST,
|
||||
"http://mock-mt5bridge:8080/gvar/MY_KEY",
|
||||
json={"name": "MY_KEY", "value": 75.5},
|
||||
status=200,
|
||||
)
|
||||
ex = mt5bridge_ccxt.mt5bridge(exchange_config)
|
||||
result = ex.mql5.set("MY_KEY", 75.5)
|
||||
assert result["name"] == "MY_KEY"
|
||||
|
||||
@responses.activate
|
||||
def test_alpha_trend_signal(self, exchange_config):
|
||||
# Mock 5 GV lookups
|
||||
gv_data = {
|
||||
"AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Alpha": {"name": "AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Alpha", "value": 4180.0},
|
||||
"AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Offset": {"name": "AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Offset", "value": 4178.0},
|
||||
"AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Trend": {"name": "AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Trend", "value": 1.0},
|
||||
"AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Buy": {"name": "AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Buy", "value": 1.0},
|
||||
"AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Sell": {"name": "AT_XAUUSDc_PERIOD_H1_L14_A1.0_C0_S1_Sell", "value": 0.0},
|
||||
}
|
||||
for path, payload in gv_data.items():
|
||||
responses.add(
|
||||
responses.GET,
|
||||
f"http://mock-mt5bridge:8080/gvar/{path}",
|
||||
json=payload, status=200,
|
||||
)
|
||||
|
||||
ex = mt5bridge_ccxt.mt5bridge(exchange_config)
|
||||
signal = ex.mql5.alpha_trend_signal("XAUUSDc", "H1", length=14, atr_mult=1.0)
|
||||
assert signal["alpha"] == 4180.0
|
||||
assert signal["trend"] == 1.0
|
||||
assert signal["buy"] == 1.0
|
||||
assert signal["sell"] == 0.0
|
||||
|
||||
|
||||
class TestTimeframeConversion:
|
||||
def test_to_mt5(self):
|
||||
from mt5bridge_ccxt.timeframe import to_mt5
|
||||
assert to_mt5("1m") == "TIMEFRAME_M1"
|
||||
assert to_mt5("1h") == "TIMEFRAME_H1"
|
||||
assert to_mt5("1d") == "TIMEFRAME_D1"
|
||||
|
||||
def test_to_mt5_invalid(self):
|
||||
from mt5bridge_ccxt.timeframe import to_mt5
|
||||
with pytest.raises(ValueError):
|
||||
to_mt5("2h")
|
||||
|
||||
def test_to_ccxt(self):
|
||||
from mt5bridge_ccxt.timeframe import to_ccxt
|
||||
assert to_ccxt("TIMEFRAME_M1") == "1m"
|
||||
assert to_ccxt("TIMEFRAME_H1") == "1h"
|
||||
assert to_ccxt("TIMEFRAME_D1") == "1d"
|
||||
|
||||
|
||||
class TestSymbolConversion:
|
||||
def test_to_mt5_with_slash(self):
|
||||
from mt5bridge_ccxt.symbol import to_mt5_symbol
|
||||
assert to_mt5_symbol("XAU/USD") == "XAUUSD"
|
||||
assert to_mt5_symbol("EUR/USD") == "EURUSD"
|
||||
|
||||
def test_to_mt5_already_mt5(self):
|
||||
from mt5bridge_ccxt.symbol import to_mt5_symbol
|
||||
assert to_mt5_symbol("XAUUSDc") == "XAUUSDc"
|
||||
|
||||
def test_to_mt5_with_suffix(self):
|
||||
from mt5bridge_ccxt.symbol import to_mt5_symbol
|
||||
assert to_mt5_symbol("XAU/USD", default_suffix="c") == "XAUUSDc"
|
||||
|
||||
def test_to_ccxt_simple(self):
|
||||
from mt5bridge_ccxt.symbol import to_ccxt_symbol
|
||||
assert to_ccxt_symbol("XAUUSD") == "XAU/USD"
|
||||
assert to_ccxt_symbol("EURUSD") == "EUR/USD"
|
||||
|
||||
def test_to_ccxt_with_suffix(self):
|
||||
from mt5bridge_ccxt.symbol import to_ccxt_symbol
|
||||
assert to_ccxt_symbol("XAUUSDc") == "XAU/USD"
|
||||
assert to_ccxt_symbol("EURUSDc") == "EUR/USD"
|
||||
|
||||
def test_to_ccxt_with_explicit_quote(self):
|
||||
from mt5bridge_ccxt.symbol import to_ccxt_symbol
|
||||
# Ambiguous case: split on explicit quote
|
||||
assert to_ccxt_symbol("XAUUSD", quote="USD") == "XAU/USD"
|
||||
Reference in New Issue
Block a user