#!/usr/bin/env python3
"""
═══════════════════════════════════════════════════════════════
📈 PROGRESS BUILDER - ICHIGRIDEA PIPELINE
═══════════════════════════════════════════════════════════════
Construit la vue de progression et les KPIs du projet.

Usage:
    python progress_builder.py --build
    python progress_builder.py --kpi
    python progress_builder.py --dashboard
"""

import json
import os
from datetime import datetime
from pathlib import Path
from collections import defaultdict


class ProgressBuilder:
    def __init__(self, base_dir: str = "."):
        self.base_dir = Path(base_dir)
        self.include_dir = self.base_dir / "Include"
        
        # Charger les registres
        self.state = self._load_json("STATE.json")
        self.modules_registry = self._load_json("MODULES_REGISTRY.json")
        self.mapping = self._load_json("MAPPING.json")
        
    def _load_json(self, filename: str) -> dict:
        """Charge un fichier JSON"""
        filepath = self.base_dir / filename
        if filepath.exists():
            with open(filepath, "r", encoding="utf-8") as f:
                return json.load(f)
        return {}
    
    def _count_lines(self, filepath: Path) -> int:
        """Compte les lignes d'un fichier"""
        try:
            with open(filepath, "r", encoding="utf-8", errors="ignore") as f:
                return sum(1 for _ in f)
        except:
            return 0
    
    def build_progress(self) -> dict:
        """Construit la vue de progression"""
        progress = {
            "timestamp": datetime.utcnow().isoformat() + "Z",
            "overview": {},
            "by_category": {},
            "by_status": {},
            "modules": [],
            "kpis": {}
        }
        
        # Compter les modules
        modules = list(self.include_dir.glob("*.mqh"))
        total_modules = len(modules)
        total_lines = sum(self._count_lines(m) for m in modules)
        
        # Modules avec header de traçabilité
        modules_with_header = 0
        modules_with_section = 0
        
        for module in modules:
            content = ""
            try:
                with open(module, "r", encoding="utf-8", errors="ignore") as f:
                    content = f.read(2000)
            except:
                pass
            
            if "@section" in content:
                modules_with_section += 1
            if "gen:header" in content:
                modules_with_header += 1
            
            # Ajouter au détail
            progress["modules"].append({
                "name": module.stem,
                "lines": self._count_lines(module),
                "has_section": "@section" in content,
                "has_header": "gen:header" in content,
                "status": "complete" if "gen:header" in content else "legacy"
            })
        
        # Overview
        progress["overview"] = {
            "total_modules": total_modules,
            "total_lines": total_lines,
            "modules_with_header": modules_with_header,
            "modules_with_section": modules_with_section,
            "header_coverage": round(modules_with_header / total_modules * 100, 1) if total_modules > 0 else 0,
            "section_coverage": round(modules_with_section / total_modules * 100, 1) if total_modules > 0 else 0
        }
        
        # Par statut
        progress["by_status"] = {
            "complete": modules_with_header,
            "legacy": total_modules - modules_with_header
        }
        
        # Catégories depuis le registre
        registry_modules = self.modules_registry.get("modules", {})
        categories = defaultdict(int)
        for module_name, info in registry_modules.items():
            cat = info.get("category", "other")
            categories[cat] += 1
        progress["by_category"] = dict(categories)
        
        # KPIs
        progress["kpis"] = self._calculate_kpis(progress)
        
        return progress
    
    def _calculate_kpis(self, progress: dict) -> dict:
        """Calcule les KPIs"""
        overview = progress.get("overview", {})
        
        return {
            "completion_rate": overview.get("header_coverage", 0),
            "total_modules": overview.get("total_modules", 0),
            "total_lines": overview.get("total_lines", 0),
            "avg_lines_per_module": round(overview.get("total_lines", 0) / max(overview.get("total_modules", 1), 1), 0),
            "modules_to_update": overview.get("total_modules", 0) - overview.get("modules_with_header", 0),
            "health_score": self._calculate_health_score(progress)
        }
    
    def _calculate_health_score(self, progress: dict) -> int:
        """Calcule un score de santé du projet (0-100)"""
        score = 100
        
        overview = progress.get("overview", {})
        
        # Pénalité pour modules sans header
        header_coverage = overview.get("header_coverage", 0)
        if header_coverage < 50:
            score -= 30
        elif header_coverage < 80:
            score -= 15
        
        # Pénalité pour modules sans section
        section_coverage = overview.get("section_coverage", 0)
        if section_coverage < 50:
            score -= 20
        elif section_coverage < 80:
            score -= 10
        
        # Bonus pour beaucoup de modules
        total_modules = overview.get("total_modules", 0)
        if total_modules >= 50:
            score += 10
        
        return max(0, min(100, score))
    
    def generate_dashboard(self) -> str:
        """Génère un dashboard ASCII"""
        progress = self.build_progress()
        overview = progress["overview"]
        kpis = progress["kpis"]
        
        dashboard = f"""
═══════════════════════════════════════════════════════════════
  📊 ICHIGRIDEA - DASHBOARD DE PROGRESSION
═══════════════════════════════════════════════════════════════
  Date: {progress['timestamp']}
═══════════════════════════════════════════════════════════════

  MODULES           {overview['total_modules']:>6}     LIGNES TOTAL     {overview['total_lines']:>8}
  Avec header       {overview['modules_with_header']:>6}     Moy/module       {kpis['avg_lines_per_module']:>8.0f}
  Avec @section     {overview['modules_with_section']:>6}     À mettre à jour  {kpis['modules_to_update']:>8}

═══════════════════════════════════════════════════════════════
  COUVERTURE
═══════════════════════════════════════════════════════════════

  Headers:   [{self._progress_bar(overview['header_coverage'])}] {overview['header_coverage']:>5.1f}%
  Sections:  [{self._progress_bar(overview['section_coverage'])}] {overview['section_coverage']:>5.1f}%

═══════════════════════════════════════════════════════════════
  SCORE DE SANTÉ: {kpis['health_score']}/100 {self._health_emoji(kpis['health_score'])}
═══════════════════════════════════════════════════════════════

  PAR STATUT
  ──────────────────────────────
"""
        for status, count in progress["by_status"].items():
            dashboard += f"  {status:15} {count:>6}\n"
        
        dashboard += """
  PAR CATÉGORIE
  ──────────────────────────────
"""
        for cat, count in sorted(progress["by_category"].items()):
            dashboard += f"  {cat:15} {count:>6}\n"
        
        dashboard += """
═══════════════════════════════════════════════════════════════
"""
        return dashboard
    
    def _progress_bar(self, percentage: float, width: int = 30) -> str:
        """Génère une barre de progression"""
        filled = int(width * percentage / 100)
        return "█" * filled + "░" * (width - filled)
    
    def _health_emoji(self, score: int) -> str:
        """Emoji selon le score"""
        if score >= 80:
            return "🟢"
        elif score >= 60:
            return "🟡"
        elif score >= 40:
            return "🟠"
        else:
            return "🔴"
    
    def save_progress(self, output_file: str = "PROGRESS.json"):
        """Sauvegarde la progression en JSON"""
        progress = self.build_progress()
        
        with open(output_file, "w", encoding="utf-8") as f:
            json.dump(progress, f, indent=2, ensure_ascii=False)
        
        print(f"✅ Progression sauvegardée: {output_file}")
        return progress
    
    def save_kpis(self, output_file: str = "pipeline/reports/kpis.json"):
        """Sauvegarde les KPIs en JSON"""
        progress = self.build_progress()
        kpis = progress["kpis"]
        kpis["timestamp"] = progress["timestamp"]
        
        os.makedirs(os.path.dirname(output_file), exist_ok=True)
        
        with open(output_file, "w", encoding="utf-8") as f:
            json.dump(kpis, f, indent=2, ensure_ascii=False)
        
        print(f"✅ KPIs sauvegardés: {output_file}")
        return kpis


if __name__ == "__main__":
    import sys
    
    builder = ProgressBuilder()
    
    if "--build" in sys.argv:
        builder.save_progress()
        
    elif "--kpi" in sys.argv:
        kpis = builder.save_kpis()
        print("\n📊 KPIs:")
        for key, value in kpis.items():
            if key != "timestamp":
                print(f"   {key}: {value}")
                
    elif "--dashboard" in sys.argv:
        dashboard = builder.generate_dashboard()
        print(dashboard)
        
    else:
        print(__doc__)
