from crewai import LLM
from user_journey_service.core.config import settings
import yaml
from pathlib import Path
import re

prompts_path = 'user_journey_service/config/prompts.yaml'

class MicrolearningDurationEstimator:
    def __init__(self):
        self.llm = LLM(
          model=f"{settings.PROVIDER}/{settings.LLM1}",
          temperature=settings.TEMPERATURE,
          api_key=settings.OPENAI_KEY1,
          api_base=settings.ENDPOINT1,
          api_version=settings.API_VERSION1,
          seed=settings.SEED,
          timeout=settings.TIMEOUT
        )
        self.prompts = self.load_prompts()
       
    def load_prompts(self):
        """Load prompts from YAML file with explicit UTF-8 encoding."""
        # Read the file content as binary first
        with open(Path(prompts_path), 'rb') as f:
            content_bytes = f.read()
        
        # Try to decode with UTF-8, fallback with error replacement
        try:
            content = content_bytes.decode('utf-8')
        except UnicodeDecodeError:
            # If UTF-8 fails, try with errors replacement
            content = content_bytes.decode('utf-8', errors='replace')
        
        # Now parse YAML from the string
        prompts = yaml.safe_load(content)
        return prompts
        
    def estimate_duration(self, input_data):
        prompt_template = self.prompts["duration_estimator"]
        prompt = prompt_template.format(
            Job_Title=input_data.Job_Title,
            Experience=input_data.Experience,
            Skills=input_data.Skills,
            topic=input_data.topic,
            Level=input_data.Level
        )
        
        messages = [
            {
                'role': 'user',
                'content': prompt,
            },
        ]

        response = self.llm.call(messages)
        duration_text = response.strip()
        
        # Extract number from response and validate
        numbers = re.findall(r'\d+', duration_text)
        if numbers:
            estimated_minutes = int(numbers[0])
        else:
            estimated_minutes = 180  # Default fallback
        
        # Cap at 360 minutes
        MAX_MINUTES = 360
        if estimated_minutes > MAX_MINUTES:
            estimated_minutes = MAX_MINUTES
        
        return str(estimated_minutes)