#!/usr/bin/env python3
"""
Script de test pour le gestionnaire de corrélation BTC
"""

import sys
import os
import time
import logging
from datetime import datetime

# Ajouter le chemin parent pour les imports
sys.path.append('..')

# Configuration du logging
logging.basicConfig(
    level=logging.INFO,
    format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
)
logger = logging.getLogger(__name__)

def test_correlation_manager():
    """Test du gestionnaire de corrélation"""
    try:
        # Import du client Hyperliquid
        from hyperliquid_client import HyperliquidClient
        from correlation_manager import BTCCorrelationManager

        # Initialiser le client
        logger.info("Initialisation du client Hyperliquid...")
        client = HyperliquidClient()

        # Créer le gestionnaire de corrélation
        logger.info("Création du gestionnaire de corrélation...")
        correlation_manager = BTCCorrelationManager(
            hyperliquid_client=client,
            lookback_periods=100
        )

        # Test 1: Calcul de corrélation pour différents symboles
        logger.info("\n" + "="*60)
        logger.info("TEST 1: Calcul des corrélations avec BTC")
        logger.info("="*60)

        test_symbols = ['ETH', 'SOL', 'ARB', 'MATIC', 'AVAX', 'BNB', 'LINK', 'UNI', 'AAVE', 'CRV', 'ALGO', 'GRT']

        correlations = {}
        for symbol in test_symbols:
            try:
                corr = correlation_manager.calculate_correlation(symbol)
                category = correlation_manager.get_correlation_category(corr)
                weight = correlation_manager.get_weight_factor(corr)

                correlations[symbol] = {
                    'correlation': corr,
                    'category': category,
                    'weight_factor': weight
                }

                logger.info(f"{symbol:6} - Corrélation: {corr:+.3f} | Catégorie: {category:10} | Facteur: {weight:.2f}x")
            except Exception as e:
                logger.error(f"Erreur calcul corrélation {symbol}: {e}")

        # Test 2: Mise à jour globale des corrélations
        logger.info("\n" + "="*60)
        logger.info("TEST 2: Mise à jour globale du cache")
        logger.info("="*60)

        correlation_manager.update_all_correlations(test_symbols)
        logger.info(f"Cache mis à jour avec {len(correlation_manager.correlation_cache)} symboles")

        # Test 3: Test de pondération de position
        logger.info("\n" + "="*60)
        logger.info("TEST 3: Calcul de pondération de positions")
        logger.info("="*60)

        base_size = 1000  # $1000 de position de base

        for symbol in ['ETH', 'SOL', 'ALGO', 'GRT']:
            adjusted_size = correlation_manager.get_position_weight(symbol, base_size)
            logger.info(f"{symbol}: ${base_size:.2f} -> ${adjusted_size:.2f} (ajusté par corrélation)")

        # Test 4: Vérification des limites d'exposition
        logger.info("\n" + "="*60)
        logger.info("TEST 4: Vérification des limites d'exposition")
        logger.info("="*60)

        # Simuler un portefeuille avec plusieurs positions
        current_positions = {
            'ETH': {'size': 0.5, 'entry_price': 2500, 'leverage': 5, 'side': 'LONG'},
            'SOL': {'size': 10, 'entry_price': 100, 'leverage': 10, 'side': 'LONG'},
            'BNB': {'size': 3, 'entry_price': 300, 'leverage': 5, 'side': 'LONG'}
        }

        # Tester l'ajout de nouvelles positions
        test_new_symbols = ['ARB', 'MATIC', 'LINK', 'ALGO']

        for symbol in test_new_symbols:
            allowed, reason = correlation_manager.should_open_position(symbol, current_positions)
            status = "✅ AUTORISÉ" if allowed else "❌ BLOQUÉ"
            logger.info(f"{symbol}: {status} - {reason}")

        # Test 5: Métriques du portefeuille
        logger.info("\n" + "="*60)
        logger.info("TEST 5: Métriques du portefeuille")
        logger.info("="*60)

        metrics = correlation_manager.get_portfolio_metrics(current_positions)
        logger.info(f"Corrélation moyenne: {metrics['avg_correlation']:.3f}")
        logger.info(f"Corrélation maximale: {metrics['max_correlation']:.3f}")
        logger.info(f"Score de diversification: {metrics['diversification_score']:.3f}")
        logger.info(f"Concentration du risque: {metrics['risk_concentration']:.2%}")
        logger.info(f"Positions fortement corrélées: {metrics['high_corr_positions']}/{metrics['total_positions']}")

        # Test 6: Distribution recommandée
        logger.info("\n" + "="*60)
        logger.info("TEST 6: Distribution recommandée des positions")
        logger.info("="*60)

        # Créer des signaux de test
        test_signals = [
            {'symbol': 'ETH', 'side': 'LONG', 'score': 0.85, 'current_price': 2500},
            {'symbol': 'SOL', 'side': 'LONG', 'score': 0.80, 'current_price': 100},
            {'symbol': 'ALGO', 'side': 'LONG', 'score': 0.75, 'current_price': 0.5},
            {'symbol': 'GRT', 'side': 'LONG', 'score': 0.70, 'current_price': 0.3},
            {'symbol': 'ARB', 'side': 'LONG', 'score': 0.72, 'current_price': 1.5},
            {'symbol': 'MATIC', 'side': 'LONG', 'score': 0.68, 'current_price': 0.8}
        ]

        available_balance = 10000  # $10,000 disponible

        recommended = correlation_manager.get_recommended_position_distribution(
            available_balance,
            test_signals
        )

        logger.info(f"\nBalance disponible: ${available_balance:,.2f}")
        logger.info(f"Positions recommandées: {len(recommended)}\n")

        for signal in recommended:
            logger.info(f"{signal['symbol']:6} | "
                       f"Score: {signal['score']:.2f} -> {signal['adjusted_score']:.2f} | "
                       f"Corrélation: {signal['correlation']:+.3f} ({signal['correlation_category']}) | "
                       f"Taille: ${signal['position_size']:,.2f} ({signal['position_percent']:.1f}%)")

        # Afficher les signaux ignorés
        skipped = [s for s in test_signals if s['symbol'] not in [r['symbol'] for r in recommended]]
        if skipped:
            logger.info("\nSignaux ignorés:")
            for signal in skipped:
                skip_reason = signal.get('skip_reason', 'Non sélectionné')
                logger.info(f"  - {signal['symbol']}: {skip_reason}")

        # Test 7: Test de performance (optionnel)
        logger.info("\n" + "="*60)
        logger.info("TEST 7: Test de performance")
        logger.info("="*60)

        start = time.time()
        for _ in range(10):
            correlation_manager.calculate_correlation('ETH')
        elapsed = time.time() - start

        logger.info(f"Temps moyen par calcul de corrélation: {(elapsed/10)*1000:.2f} ms")

        # Test du cache
        correlation_manager.cache_duration = 1  # Cache de 1 seconde pour test
        correlation_manager.update_all_correlations(test_symbols[:5])

        start = time.time()
        for _ in range(100):
            correlation_manager.get_position_weight('ETH', 1000)
        elapsed = time.time() - start

        logger.info(f"Temps moyen avec cache: {(elapsed/100)*1000:.3f} ms")

        logger.info("\n" + "="*60)
        logger.info("✅ TOUS LES TESTS RÉUSSIS")
        logger.info("="*60)

    except ImportError as e:
        logger.error(f"Erreur d'import: {e}")
        logger.info("Assurez-vous que hyperliquid_client.py est accessible")
    except Exception as e:
        logger.error(f"Erreur lors des tests: {e}", exc_info=True)

if __name__ == "__main__":
    test_correlation_manager()