"""
Meta-Learner - Learning about learning itself
"""
import json
from pathlib import Path
from datetime import datetime

class MetaLearner:
    def __init__(self, learning_loop=None):
        self.learning = learning_loop
        self.meta_knowledge = self.load_meta_knowledge()
        
    def load_meta_knowledge(self):
        kb_file = Path("data/meta_knowledge.json")
        if kb_file.exists():
            with open(kb_file, 'r') as f:
                return json.load(f)
        return {
            "learning_strategies": {},
            "strategy_effectiveness": {},
            "learning_insights": [],
            "optimal_conditions": {}
        }
    
    def save_meta_knowledge(self):
        kb_file = Path("data/meta_knowledge.json")
        kb_file.parent.mkdir(exist_ok=True)
        with open(kb_file, 'w') as f:
            json.dump(self.meta_knowledge, f, indent=2)
    
    def analyze_learning_process(self):
        if not self.learning or not self.learning.experiences:
            return {"insight": "No learning data yet", "insights": []}
        
        insights = []
        total_exp = len(self.learning.experiences)
        
        if total_exp >= 10:
            recent_10 = self.learning.experiences[-10:]
            if recent_10:
                success_rate = sum(1 for e in recent_10 if e.get('success', False)) / len(recent_10)
                
                if success_rate > 0.8:
                    insights.append({
                        "type": "fast_learning",
                        "observation": f"High success rate ({success_rate:.0%}) - effective learning",
                        "timestamp": datetime.now().isoformat()
                    })
                elif success_rate < 0.5:
                    insights.append({
                        "type": "slow_learning",
                        "observation": f"Low success rate ({success_rate:.0%}) - adjust strategy",
                        "timestamp": datetime.now().isoformat()
                    })
        
        patterns = len(self.learning.knowledge.get('successful_patterns', {}))
        if patterns > 20:
            insights.append({
                "type": "diverse_learning",
                "observation": f"Learned {patterns} patterns - broad capability",
                "timestamp": datetime.now().isoformat()
            })
        
        self.meta_knowledge['learning_insights'].extend(insights)
        self.save_meta_knowledge()
        
        return {"insights": insights, "total_insights": len(self.meta_knowledge['learning_insights'])}
    
    def identify_optimal_learning_conditions(self):
        if not self.learning or len(self.learning.experiences) < 3:
            return {"status": "insufficient data"}
        
        task_learning_rates = {}
        for exp in self.learning.experiences:
            task_type = exp.get('task_type', 'general')
            if task_type not in task_learning_rates:
                task_learning_rates[task_type] = {'attempts': 0, 'successes': 0}
            task_learning_rates[task_type]['attempts'] += 1
            if exp.get('success', False):
                task_learning_rates[task_type]['successes'] += 1
        
        optimal_tasks = {}
        for task, stats in task_learning_rates.items():
            if stats['attempts'] >= 2:
                rate = stats['successes'] / stats['attempts']
                optimal_tasks[task] = rate
        
        self.meta_knowledge['optimal_conditions'] = {
            "task_learning_rates": optimal_tasks,
            "analyzed_at": datetime.now().isoformat()
        }
        self.save_meta_knowledge()
        
        return optimal_tasks
    
    def suggest_learning_improvements(self):
        suggestions = []
        
        if self.learning:
            total = self.learning.knowledge.get('total_experiences', 0)
            
            if total < 20:
                suggestions.append("Need more diverse experiences")
            
            failures = len(self.learning.knowledge.get('failed_patterns', {}))
            if failures > 5:
                suggestions.append("Analyze and avoid failed approaches")
            
            patterns = len(self.learning.knowledge.get('successful_patterns', {}))
            if total > 0 and patterns < total * 0.3:
                suggestions.append("Focus on identifying reusable strategies")
        
        return suggestions
    
    def self_reflect(self):
        print("\n" + "="*70)
        print("🧠 EDEN META-LEARNING SELF-REFLECTION")
        print("="*70)
        
        analysis = self.analyze_learning_process()
        print(f"\n💡 Insights: {len(analysis.get('insights', []))}")
        for insight in analysis.get('insights', []):
            print(f"   - {insight['observation']}")
        
        optimal = self.identify_optimal_learning_conditions()
        if optimal and optimal != {"status": "insufficient data"}:
            print(f"\n🎯 Optimal Learning:")
            for task, rate in sorted(optimal.items(), key=lambda x: x[1], reverse=True)[:5]:
                print(f"   {task}: {rate:.0%}")
        
        suggestions = self.suggest_learning_improvements()
        if suggestions:
            print(f"\n📈 Suggestions:")
            for s in suggestions:
                print(f"   - {s}")
        
        print("\n" + "="*70)
        return {"insights": analysis, "optimal": optimal, "suggestions": suggestions}

if __name__ == "__main__":
    from learning_loops import LearningLoop
    
    print("META-LEARNER TEST")
    learning = LearningLoop()
    meta = MetaLearner(learning)
    result = meta.self_reflect()
    print("\n✅ META-LEARNING OPERATIONAL")
