from decimal import Decimal

from src.reconciliation.hyperliquid_reconciler import LocalOrderRecord, ReconcilerSnapshot, reconcile_hyperliquid_state


def test_reconciler_flags_exchange_position_without_local_journal_and_bad_stop_direction_size():
    snapshot = ReconcilerSnapshot(
        positions={"BTC": {"coin": "BTC", "szi": "0.02", "side": "long"}},
        open_orders=[{"coin": "BTC", "reduceOnly": True, "orderType": "trigger", "side": "buy", "sz": "0.01"}],
        local_orders=[],
    )

    result = reconcile_hyperliquid_state(snapshot, max_position_notional_usd=1000, mids={"BTC": 100000})

    assert result.block_new_entries is True
    assert result.severity == "CRITICAL"
    assert "exchange_position_without_local_journal:BTC" in result.alerts
    assert "stop_wrong_direction:BTC" in result.alerts
    assert "stop_wrong_size:BTC" in result.alerts
    assert "position_exposure_exceeded:BTC" in result.alerts
    assert any(action["action"] == "prepare_telegram_alert" for action in result.recommended_actions)


def test_reconciler_flags_local_journal_without_exchange_position_and_entry_without_deadman():
    snapshot = ReconcilerSnapshot(
        positions={},
        open_orders=[{"coin": "ETH", "reduceOnly": False, "orderType": "limit", "side": "buy", "deadmanProtected": False}],
        local_orders=[LocalOrderRecord(coin="BTC", client_order_id="entry-1", order_role="entry")],
    )

    result = reconcile_hyperliquid_state(snapshot)

    assert "local_journal_position_without_exchange_position:BTC" in result.alerts
    assert "entry_order_without_deadman:ETH" in result.alerts


def test_reconciler_accepts_hyperliquid_reduce_only_stop_payload_without_order_type():
    snapshot = ReconcilerSnapshot(
        positions={"BTC": {"coin": "BTC", "szi": "0.00024", "side": "long"}},
        open_orders=[{"coin": "BTC", "reduceOnly": True, "side": "A", "sz": "0.00024", "origSz": "0.00024", "limitPx": "61608"}],
        local_orders=[LocalOrderRecord(coin="BTC", client_order_id="entry-1", order_role="entry", size=Decimal("0.00024"))],
    )

    result = reconcile_hyperliquid_state(snapshot, max_position_notional_usd=100, mids={"BTC": 62000})

    assert result.stops_missing_count == 0
    assert "position_without_stop:BTC" not in result.alerts
    assert "stop_wrong_direction:BTC" not in result.alerts
    assert "stop_wrong_size:BTC" not in result.alerts
