"""
Recipe models for chocolate tempering process management.
"""

from datetime import datetime, timezone
from enum import Enum
from typing import Optional
from uuid import uuid4

from sqlalchemy import Column, DateTime, Enum as SQLEnum, Float, ForeignKey, Integer, String, Text, Boolean
from sqlalchemy.orm import relationship

from ..database import Base


class RecipePhase(str, Enum):
    """Chocolate tempering process phases."""
    PREHEATING = "preheating"
    HEATING = "heating" 
    HEATING_DELAY = "heating_delay"
    COOLING = "cooling"
    COOLING_DELAY = "cooling_delay"
    POURING = "pouring"
    COMPLETED = "completed"
    STOPPED = "stopped"
    ERROR = "error"


class Recipe(Base):
    """
    Recipe configuration for chocolate tempering process.
    Based on the original RecipeTable.csv structure.
    """
    __tablename__ = "recipes"

    # Primary identification
    id = Column(Integer, primary_key=True, index=True)
    name = Column(String(100), nullable=False, unique=True, index=True)
    description = Column(Text, nullable=True)
    
    # Temperature goals (°C)
    heating_goal = Column(Float, nullable=False, comment="Target heating temperature (°C)")
    cooling_goal = Column(Float, nullable=False, comment="Target cooling temperature (°C)") 
    pouring_goal = Column(Float, nullable=True, comment="Target pouring temperature (°C)")
    
    # Tank and fountain temperature settings
    tank_temp = Column(Float, nullable=False, default=45.0, comment="Tank operating temperature (°C)")
    fountain_temp = Column(Float, nullable=False, default=32.0, comment="Fountain operating temperature (°C)")
    
    # Motor control settings (boolean flags)
    mixer_enabled = Column(Boolean, nullable=False, default=True, comment="Enable mixer motor")
    fountain_enabled = Column(Boolean, nullable=False, default=True, comment="Enable fountain motor")
    mold_heater_enabled = Column(Boolean, nullable=False, default=False, comment="Enable mold heater")
    vibration_enabled = Column(Boolean, nullable=False, default=False, comment="Enable vibration motor")
    vib_heater_enabled = Column(Boolean, nullable=False, default=False, comment="Enable vibration heater")
    
    # Pedal control settings
    pedal_control_enabled = Column(Boolean, nullable=False, default=True, comment="Enable pedal control")
    pedal_on_time = Column(Float, nullable=False, default=2.0, comment="Pedal on duration (seconds)")
    pedal_off_time = Column(Float, nullable=False, default=3.0, comment="Pedal off duration (seconds)")
    
    # Recipe metadata
    created_at = Column(DateTime(timezone=True), default=lambda: datetime.now(timezone.utc))
    updated_at = Column(DateTime(timezone=True), default=lambda: datetime.now(timezone.utc), onupdate=lambda: datetime.now(timezone.utc))
    created_by = Column(String(50), nullable=True, comment="User who created the recipe")
    version = Column(Integer, nullable=False, default=1, comment="Recipe version number")
    is_active = Column(Boolean, nullable=False, default=True, comment="Recipe is active and can be used")
    
    # Usage statistics
    usage_count = Column(Integer, nullable=False, default=0, comment="Number of times recipe was used")
    last_used = Column(DateTime(timezone=True), nullable=True, comment="Last time recipe was used")
    
    # Relationships
    process_sessions = relationship("ProcessSession", back_populates="recipe")

    def __repr__(self) -> str:
        return f"<Recipe(id={self.id}, name='{self.name}', heating_goal={self.heating_goal}, cooling_goal={self.cooling_goal})>"
    
    def validate_temperatures(self) -> bool:
        """Validate recipe temperature parameters."""
        # Cooling goal must be less than heating goal
        if self.cooling_goal >= self.heating_goal:
            return False
        
        # Temperature ranges validation
        if not (20.0 <= self.cooling_goal <= 40.0):
            return False
            
        if not (40.0 <= self.heating_goal <= 60.0):
            return False
            
        # Optional pouring goal validation
        if self.pouring_goal is not None:
            if not (self.cooling_goal <= self.pouring_goal <= self.heating_goal):
                return False
        
        return True
    
    def get_phase_sequence(self) -> list[RecipePhase]:
        """Get the sequence of phases for this recipe."""
        return [
            RecipePhase.PREHEATING,
            RecipePhase.HEATING,
            RecipePhase.HEATING_DELAY,
            RecipePhase.COOLING,
            RecipePhase.COOLING_DELAY,
            RecipePhase.POURING
        ]
    
    def to_dict(self) -> dict:
        """Convert recipe to dictionary."""
        return {
            "id": self.id,
            "name": self.name,
            "description": self.description,
            "heating_goal": self.heating_goal,
            "cooling_goal": self.cooling_goal,
            "pouring_goal": self.pouring_goal,
            "tank_temp": self.tank_temp,
            "fountain_temp": self.fountain_temp,
            "mixer_enabled": self.mixer_enabled,
            "fountain_enabled": self.fountain_enabled,
            "mold_heater_enabled": self.mold_heater_enabled,
            "vibration_enabled": self.vibration_enabled,
            "vib_heater_enabled": self.vib_heater_enabled,
            "pedal_control_enabled": self.pedal_control_enabled,
            "pedal_on_time": self.pedal_on_time,
            "pedal_off_time": self.pedal_off_time,
            "created_at": self.created_at.isoformat() if self.created_at else None,
            "updated_at": self.updated_at.isoformat() if self.updated_at else None,
            "created_by": self.created_by,
            "version": self.version,
            "is_active": self.is_active,
            "usage_count": self.usage_count,
            "last_used": self.last_used.isoformat() if self.last_used else None,
        }
    
    @classmethod
    def from_csv_row(cls, row: dict) -> "Recipe":
        """Create Recipe instance from CSV row data (migration utility)."""
        return cls(
            id=int(row.get("ID", 0)),
            name=row.get("Name", "Unknown Recipe"),
            heating_goal=float(row.get("HeatingGoal", 46.0)),
            cooling_goal=float(row.get("CoolingGoal", 27.0)),
            pouring_goal=float(row.get("PouringGoal", 30.0)) if row.get("PouringGoal") else None,
            tank_temp=float(row.get("TankTemp", 45.0)),
            fountain_temp=float(row.get("FountainTemp", 32.0)),
            mixer_enabled=bool(int(row.get("Mixer", 1))),
            fountain_enabled=bool(int(row.get("Fountain", 1))),
            mold_heater_enabled=bool(int(row.get("MoldHeater", 0))),
            vibration_enabled=bool(int(row.get("Vibration", 0))),
            vib_heater_enabled=bool(int(row.get("VibHeater", 0))),
            pedal_control_enabled=bool(int(row.get("Pedal", 1))),
            pedal_on_time=float(row.get("PedalOnTime", 2.0)),
            pedal_off_time=float(row.get("PedalOffTime", 3.0)),
        )