"""Historical data fetching and conversion utilities."""

from __future__ import annotations

from horizon._horizon import (
    OHLCBar,
    fetch_polymarket_prices,
    fetch_polymarket_trades,
)
from horizon.backtest import Tick


def fetch_prices(
    token_id: str,
    start: str | float,
    end: str | float,
    fidelity: int = 60,
) -> list[dict]:
    """Fetch Polymarket OHLC history.

    Args:
        token_id: Polymarket token ID (condition_id or token_id).
        start: Start timestamp (UNIX float or ISO string).
        end: End timestamp (UNIX float or ISO string).
        fidelity: Bar interval in seconds (default 60).

    Returns:
        List of dicts compatible with hz.backtest(data=...).
    """
    start_ts = _parse_ts(start)
    end_ts = _parse_ts(end)
    bars = fetch_polymarket_prices(token_id, start_ts, end_ts, fidelity)
    return [
        {
            "timestamp": bar.timestamp,
            "price": bar.close,
            "bid": min(bar.open, bar.close),
            "ask": max(bar.open, bar.close),
            "volume": bar.volume,
        }
        for bar in bars
    ]


def fetch_trades(token_id: str, limit: int = 1000) -> list[dict]:
    """Fetch Polymarket trade history.

    Args:
        token_id: Polymarket token ID.
        limit: Maximum number of trades to fetch.

    Returns:
        List of trade dicts with timestamp, price, size, side, market_id.
    """
    trades = fetch_polymarket_trades(token_id, limit)
    return [
        {
            "timestamp": t.timestamp,
            "price": t.price,
            "size": t.size,
            "side": t.side,
            "market_id": t.market_id,
        }
        for t in trades
    ]


def ohlc_to_ticks(bars: list[OHLCBar]) -> list[Tick]:
    """Convert OHLCBar list to backtest Tick list.

    Uses close as price, min(open, close) as bid, max(open, close) as ask.
    """
    return [
        Tick(
            timestamp=bar.timestamp,
            price=bar.close,
            bid=min(bar.open, bar.close),
            ask=max(bar.open, bar.close),
            volume=bar.volume,
        )
        for bar in bars
    ]


def _parse_ts(value: str | float) -> float:
    """Parse a timestamp value to float UNIX time."""
    if isinstance(value, (int, float)):
        return float(value)
    # Try ISO format parsing
    from datetime import datetime

    try:
        dt = datetime.fromisoformat(value.replace("Z", "+00:00"))
        return dt.timestamp()
    except (ValueError, AttributeError):
        try:
            return float(value)
        except (ValueError, TypeError) as e:
            raise ValueError(f"Cannot parse timestamp: {value!r}") from e
