"""
Diagnostic Utilities for TradePose Strategy Configuration

Provides tools for inspecting strategy requirements before execution.
"""

from typing import List, Set, Tuple

from tradepose_models.strategy import StrategyConfig


def inspect_strategy_data_requirements(config: StrategyConfig) -> None:
    """Inspect and display all required (instrument, frequency) pairs for a strategy.

    This utility parses a StrategyConfig and prints all instruments and frequencies
    that must have data available in the database for the strategy to execute.
    Use this before running a backtest to verify data availability.

    Args:
        config: StrategyConfig instance to inspect

    Example:
        >>> from tradepose_client import TradePoseClient
        >>> from tradepose_client.diagnostics import inspect_strategy_data_requirements
        >>>
        >>> client = TradePoseClient(api_url="http://localhost:8001", api_key="...")
        >>> strategy = client.strategies.get(name="my_strategy")
        >>> inspect_strategy_data_requirements(strategy)
        Required instruments and frequencies:
          ✓ FTMO:swap:XAUUSD (base) @ 15min
          ✓ FTMO:swap:US100.cash (indicator: 4h_RAW_OHLCV|low) @ 4h
          ✓ FTMO:swap:XAUUSD (indicator: 1D_ATR|14) @ 1D

    Note:
        - The base instrument must always have data at the base frequency
        - Cross-instrument indicators require the source instrument to have data
        - Cross-frequency indicators require data to be available at that frequency
    """
    print("\n" + "=" * 70)
    print("📋 Strategy Data Requirements Inspection")
    print("=" * 70)
    print(f"Strategy: {config.name}")
    print(f"Base instrument: {config.base_instrument}")
    print(f"Base frequency: {config.base_freq.value}")
    print()

    # Collect all unique (instrument, freq) pairs
    requirements: Set[Tuple[str, str]] = set()

    # Add base instrument requirement
    requirements.add((config.base_instrument, config.base_freq.value))

    # Add indicator requirements
    indicator_details: List[Tuple[str, str, str]] = []  # (instrument, freq, display_name)
    for spec in config.indicators:
        instrument = spec.instrument or config.base_instrument
        freq = spec.freq.value
        display_name = spec.display_name()

        requirements.add((instrument, freq))
        indicator_details.append((instrument, freq, display_name))

    # Display results
    print("Required instruments and frequencies:")
    print()

    # First, show base instrument
    print(f"  ✓ {config.base_instrument} (base) @ {config.base_freq.value}")

    # Then, show cross-instrument or cross-frequency indicators
    seen_cross_pairs = {(config.base_instrument, config.base_freq.value)}
    for instrument, freq, display_name in indicator_details:
        pair = (instrument, freq)
        if pair not in seen_cross_pairs:
            print(f"  ✓ {instrument} (indicator: {display_name}) @ {freq}")
            seen_cross_pairs.add(pair)

    print()
    print(f"Total unique instrument-frequency pairs: {len(requirements)}")
    print("=" * 70)
    print()
    print("💡 Troubleshooting:")
    print("  - If backtest fails with 'MissingData' error, verify these instruments")
    print("    have OHLCV data in data.ohlcv table for the specified frequencies")
    print("  - Check data.instruments table for correct instrument definitions")
    print("  - Verify OHLCV ingestion completed for required date ranges")
    print()


def list_strategy_indicators(config: StrategyConfig) -> None:
    """List all indicators defined in a strategy with their configurations.

    Args:
        config: StrategyConfig instance to inspect

    Example:
        >>> from tradepose_client.diagnostics import list_strategy_indicators
        >>> list_strategy_indicators(strategy)
        Strategy: my_strategy
        Indicators (3):
          [0] 1D_ATR|14
              - Type: ATR
              - Instrument: FTMO:swap:XAUUSD
              - Frequency: 1D
              - Shift: 1
              - Config: {'period': 14}
    """
    print("\n" + "=" * 70)
    print("📊 Strategy Indicators")
    print("=" * 70)
    print(f"Strategy: {config.name}")
    print(f"Total indicators: {len(config.indicators)}")
    print()

    if not config.indicators:
        print("  (No indicators defined)")
        print()
        return

    for idx, spec in enumerate(config.indicators):
        instrument = spec.instrument or config.base_instrument
        display_name = spec.display_name()
        indicator_type = spec.indicator.type
        freq = spec.freq.value
        shift = spec.shift

        print(f"  [{idx}] {display_name}")
        print(f"      - Type: {indicator_type}")
        print(f"      - Instrument: {instrument}")
        print(f"      - Frequency: {freq}")
        print(f"      - Shift: {shift}")

        # Show indicator config (exclude 'type' field)
        config_dict = spec.indicator.model_dump(exclude={"type"})
        if config_dict:
            print(f"      - Config: {config_dict}")
        print()

    print("=" * 70)
    print()
