"""
Avatar Studio Service

Service for creating talking avatars using InfiniteTalk and Hunyuan Avatar.
Supports both models with automatic selection or explicit model choice.
"""

from typing import Dict, Any, Optional
from fastapi import HTTPException
from loguru import logger

from services.image_studio.infinitetalk_adapter import InfiniteTalkService
from services.video_studio.hunyuan_avatar_adapter import HunyuanAvatarService
from utils.logger_utils import get_service_logger
from services.llm_providers.main_video_generation import _track_video_operation_usage

logger = get_service_logger("video_studio.avatar")


class AvatarStudioService:
    """Service for Avatar Studio operations using InfiniteTalk and Hunyuan Avatar."""
    
    def __init__(self):
        """Initialize Avatar Studio service."""
        self.infinitetalk_service = InfiniteTalkService()
        self.hunyuan_avatar_service = HunyuanAvatarService()
        logger.info("[AvatarStudio] Service initialized with InfiniteTalk and Hunyuan Avatar")
    
    async def create_talking_avatar(
        self,
        image_base64: str,
        audio_base64: str,
        resolution: str = "720p",
        prompt: Optional[str] = None,
        mask_image_base64: Optional[str] = None,
        seed: Optional[int] = None,
        user_id: str = "video_studio",
        model: str = "infinitetalk",
        progress_callback: Optional[callable] = None,
    ) -> Dict[str, Any]:
        """
        Create talking avatar video using InfiniteTalk or Hunyuan Avatar.
        
        Args:
            image_base64: Person image in base64 or data URI
            audio_base64: Audio file in base64 or data URI
            resolution: Output resolution (480p or 720p)
            prompt: Optional prompt for expression/style
            mask_image_base64: Optional mask for animatable regions (InfiniteTalk only)
            seed: Optional random seed
            user_id: User ID for tracking
            model: Model to use - "infinitetalk" (default) or "hunyuan-avatar"
            progress_callback: Optional progress callback function
            
        Returns:
            Dictionary with video_bytes, metadata, cost, and file info
        """
        logger.info(
            f"[AvatarStudio] Creating talking avatar: user={user_id}, resolution={resolution}, model={model}"
        )
        
        # PRE-FLIGHT VALIDATION: Validate video generation before API call
        # MUST happen BEFORE any API calls - return immediately if validation fails
        from services.database import get_db
        from services.subscription import PricingService
        from services.subscription.preflight_validator import validate_video_generation_operations
        
        db = next(get_db())
        try:
            pricing_service = PricingService(db)
            # Raises HTTPException immediately if validation fails - frontend gets immediate response
            validate_video_generation_operations(
                pricing_service=pricing_service,
                user_id=user_id
            )
        except HTTPException:
            # Re-raise immediately - don't proceed with API call
            logger.error(f"[AvatarStudio] ❌ Pre-flight validation failed - blocking API call")
            raise
        finally:
            db.close()
        
        import time
        start_time = time.time()
        
        try:
            if model == "hunyuan-avatar":
                # Use Hunyuan Avatar (doesn't support mask_image)
                result = await self.hunyuan_avatar_service.create_talking_avatar(
                    image_base64=image_base64,
                    audio_base64=audio_base64,
                    resolution=resolution,
                    prompt=prompt,
                    seed=seed,
                    user_id=user_id,
                    progress_callback=progress_callback,
                )
            else:
                # Default to InfiniteTalk
                result = await self.infinitetalk_service.create_talking_avatar(
                    image_base64=image_base64,
                    audio_base64=audio_base64,
                    resolution=resolution,
                    prompt=prompt,
                    mask_image_base64=mask_image_base64,
                    seed=seed,
                    user_id=user_id,
                )
            
            response_time = time.time() - start_time
            
            logger.info(
                f"[AvatarStudio] ✅ Talking avatar created: "
                f"model={model}, resolution={resolution}, duration={result.get('duration', 0)}s, "
                f"cost=${result.get('cost', 0):.2f}"
            )
            
            # TRACK USAGE after successful API call
            # Use video_bytes if available, otherwise check if result itself is bytes (unlikely, dict expected)
            video_bytes = result.get("video_bytes")
            if user_id and video_bytes:
                _track_video_operation_usage(
                    user_id=user_id,
                    provider=model, # Use model name as provider/actual_provider for now
                    model=model,
                    operation_type="talking-avatar",
                    result_bytes=video_bytes,
                    cost=result.get("cost", 0.0),
                    prompt=prompt,
                    endpoint="/avatar-generation",
                    metadata=result,
                    log_prefix="[Avatar Generation]",
                    response_time=response_time
                )
            
            return result
            
        except HTTPException:
            raise
        except Exception as e:
            logger.error(f"[AvatarStudio] ❌ Error creating talking avatar: {str(e)}", exc_info=True)
            raise HTTPException(
                status_code=500,
                detail=f"Failed to create talking avatar: {str(e)}"
            )
    
    def calculate_cost_estimate(
        self,
        resolution: str,
        estimated_duration: float,
        model: str = "infinitetalk",
    ) -> float:
        """
        Calculate estimated cost for talking avatar generation.
        
        Args:
            resolution: Output resolution (480p or 720p)
            estimated_duration: Estimated video duration in seconds
            model: Model to use - "infinitetalk" (default) or "hunyuan-avatar"
            
        Returns:
            Estimated cost in USD
        """
        if model == "hunyuan-avatar":
            return self.hunyuan_avatar_service.calculate_cost(resolution, estimated_duration)
        else:
            return self.infinitetalk_service.calculate_cost(resolution, estimated_duration)
