"""OpenHedge Python SDK — Momentum Strategy Example.

A simple momentum agent that:
1. Polls price every 60 seconds
2. Tracks a short-term moving average vs. long-term
3. Opens long positions when momentum is bullish
4. Closes positions when momentum reverses
"""

import asyncio
import logging
from collections import deque

from openhedge import OpenHedgeAgent

logging.basicConfig(level=logging.INFO, format="%(asctime)s %(message)s")
log = logging.getLogger(__name__)

# --- Configuration ---
VAULT = "0x..."  # Your vault address
PAIR = "ETH/USD"
COLLATERAL = 500_000_000  # 500 USDC
LEVERAGE = 5
SHORT_WINDOW = 5   # 5-minute fast MA
LONG_WINDOW = 20   # 20-minute slow MA
POLL_INTERVAL = 60  # seconds


async def get_nav_as_price(agent: OpenHedgeAgent, vault: str) -> float:
    """Use the vault NAV as a price proxy (in a real agent, use a price oracle)."""
    nav = await agent.vault.nav(vault)
    return nav / 1e6


async def run_strategy():
    async with OpenHedgeAgent(
        api_key="oh_your_api_key",
        wallet_private_key="0x_your_private_key",
    ) as agent:
        short_prices: deque = deque(maxlen=SHORT_WINDOW)
        long_prices: deque = deque(maxlen=LONG_WINDOW)
        in_position = False
        current_trade_index = None

        log.info("Momentum strategy started for %s on vault %s", PAIR, VAULT)

        while True:
            try:
                price = await get_nav_as_price(agent, VAULT)
                short_prices.append(price)
                long_prices.append(price)

                if len(long_prices) < LONG_WINDOW:
                    log.info(
                        "Warming up: %d/%d prices collected (current: %.4f)",
                        len(long_prices), LONG_WINDOW, price,
                    )
                    await asyncio.sleep(POLL_INTERVAL)
                    continue

                short_ma = sum(short_prices) / len(short_prices)
                long_ma = sum(long_prices) / len(long_prices)
                spread_bps = int((short_ma - long_ma) / long_ma * 10000)

                log.info(
                    "Price=%.4f  Short MA=%.4f  Long MA=%.4f  Spread=%d bps",
                    price, short_ma, long_ma, spread_bps,
                )

                # --- Entry signal: short MA crosses above long MA ---
                if not in_position and spread_bps > 50:
                    log.info("BULLISH signal — opening long %s %dx", PAIR, LEVERAGE)
                    result = await agent.trade.open_position(
                        vault=VAULT,
                        pair=PAIR,
                        is_long=True,
                        collateral=COLLATERAL,
                        leverage=LEVERAGE,
                    )
                    log.info("Position opened: %s", result.tx_hash)
                    in_position = True
                    # In production, parse the TradeOpened event for the trade index
                    current_trade_index = 0

                # --- Exit signal: short MA crosses below long MA ---
                elif in_position and spread_bps < -50:
                    log.info("BEARISH signal — closing position")
                    if current_trade_index is not None:
                        result = await agent.trade.close_trade(
                            vault=VAULT,
                            trade_index=current_trade_index,
                        )
                        log.info("Position closed: %s", result.tx_hash)
                    in_position = False
                    current_trade_index = None

            except Exception as exc:
                log.error("Strategy loop error: %s", exc)

            await asyncio.sleep(POLL_INTERVAL)


if __name__ == "__main__":
    asyncio.run(run_strategy())
