"""
Compare Strategy Outputs

Compares the CSV export from TradingView (Pine Script) against the Python strategy output.
Calculates the difference for each debug column to identify divergence.

Usage:
    python tools/compare_strategies.py --tv_data <path_to_tv_export.csv> --py_data <path_to_macro_data.csv>
"""
import pandas as pd
import argparse
import os
import sys
import importlib.util

# Add project root to sys.path
sys.path.append(os.path.abspath(os.path.join(os.path.dirname(__file__), '..')))

def main():
    parser = argparse.ArgumentParser(description="Compare TradingView vs Python Strategy")
    parser.add_argument("--tv_data", type=str, required=True, help="Path to TradingView Export CSV")
    parser.add_argument("--py_data", type=str, default="data/mlp/COINBASE_BTCUSD, 1D.csv", help="Path to Python Input Data")
    args = parser.parse_args()

    # 1. Load TradingView Data
    print(f"Loading TradingView data from {args.tv_data}...")
    df_tv = pd.read_csv(args.tv_data)
    
    # Standardize TV columns (remove special chars, lowercase)
    # TV exports usually look like "time", "open", "high", "low", "close", "Plot", "Plot.1", etc.
    # or if named: "DB_Stoch"
    df_tv.columns = df_tv.columns.str.replace(r'[^\w\s]', '', regex=True).str.replace(' ', '_')
    
    # Parse Time (TV exports ISO time usually)
    # If 'time' column exists, convert it. TV might export as 'time' or 'Time'
    time_col = [c for c in df_tv.columns if 'time' in c.lower()][0]
    df_tv[time_col] = pd.to_datetime(df_tv[time_col])
    # If TV export is UTC, ensure it's tz-naive for comparison or match Python
    if df_tv[time_col].dt.tz is not None:
        df_tv[time_col] = df_tv[time_col].dt.tz_convert(None)
        
    df_tv.set_index(time_col, inplace=True)
    print(f"TV Data Range: {df_tv.index.min()} to {df_tv.index.max()}")

    # 2. Run Python Strategy
    print(f"Running Python strategy on {args.py_data}...")
    
    # Import strategy dynamically
    strategy_path = os.path.join("strategies", "strategy_activation_scores.py")
    spec = importlib.util.spec_from_file_location("strategy_module", strategy_path)
    strategy_module = importlib.util.module_from_spec(spec)
    spec.loader.exec_module(strategy_module)
    
    df_py_input = pd.read_csv(args.py_data)
    df_py_input.columns = df_py_input.columns.str.lower().str.strip()
    df_py_result = strategy_module.generate_signals(df_py_input)
    
    df_py_result['time'] = pd.to_datetime(df_py_result['time'])
    df_py_result.set_index('time', inplace=True)
    print(f"Python Data Range: {df_py_result.index.min()} to {df_py_result.index.max()}")

    # 3. Compare
    print("\n--- Comparison Report ---")
    
    # Find common columns (starting with DB_)
    # TV columns might be named slightly differently depending on export settings
    # We look for columns in TV that contain the Python DB_ names
    
    debug_cols = [c for c in df_py_result.columns if c.startswith('DB_')]
    master_comparison = pd.DataFrame(index=df_py_result.index)
    
    for col in debug_cols:
        # Find matching column in TV
        # TV export might be "DB_Stoch" or "Plot" if not named, but we named them in Pine.
        # TV sometimes appends numbers if names collide.
        matches = [c for c in df_tv.columns if col in c]
        
        if not matches:
            print(f"[MISSING] {col} not found in TradingView export.")
            continue
            
        tv_col = matches[0]
        
        # Align data
        # Inner join on index
        aligned = pd.concat([df_py_result[col], df_tv[tv_col]], axis=1, join='inner')
        aligned.columns = [f'PY_{col}', f'TV_{col}']
        
        # Calculate Diff
        aligned[f'Diff_{col}'] = aligned[f'PY_{col}'] - aligned[f'TV_{col}']
        aligned[f'AbsDiff_{col}'] = aligned[f'Diff_{col}'].abs()
        
        # Add to master CSV
        master_comparison = master_comparison.join(aligned, how='outer')
        
        mean_diff = aligned[f'AbsDiff_{col}'].mean()
        max_diff = aligned[f'AbsDiff_{col}'].max()
        
        status = "MATCH" if mean_diff < 0.01 else "DIFF"
        print(f"[{status}] {col:<15} | Avg Diff: {mean_diff:.4f} | Max Diff: {max_diff:.4f}")

    # Save detailed comparison
    output_csv = "comparison_debug.csv"
    print(f"\nSaving detailed comparison to {output_csv}...")
    master_comparison.to_csv(output_csv)
    print("Done. Open this CSV to inspect row-by-row differences.")

if __name__ == "__main__":
    main()