import logging
import threading
import time
from typing import Optional
import requests
from config import DEFAULT_TIMEOUT, EMBED_CONVERTER_URL, USER_AGENT
from stream_uploader import UploadCancelledException

logger = logging.getLogger("Converter")


class EmbedConverter:
    """Embed converter client that transforms video URLs into iframe/embed player links via Video Scraper."""

    def __init__(self, endpoint: str = EMBED_CONVERTER_URL):
        self.endpoint = endpoint

    def convert_url(
        self,
        url: str,
        vcode: Optional[str] = None,
        cancel_event: Optional[threading.Event] = None,
        max_retries: int = 12,
        retry_delay: float = 5.0,
    ) -> Optional[str]:
        """
        Converts a provider URL (e.g. Videa, Indavideo, CDA) to embed format via Video Scraper (http://node6.lunes.host:3093/api/process).
        If the URL is already in embed format (e.g. VK video_ext.php or Videa player?f=...), returns it directly.
        """
        if not url:
            return None

        # Already final embed format (e.g. VK or already scraped Videa player with ?f= feed)
        if "video_ext.php" in url or "player?f=" in url:
            return url

        # If vcode wasn't explicitly passed, extract from URL if possible
        if not vcode and "videa.hu" in url:
            parts = url.rstrip("/").split("/")
            last_segment = parts[-1]
            if "player?v=" in last_segment:
                vcode = last_segment.split("player?v=")[-1].split("&")[0]
            elif "-" in last_segment:
                vcode = last_segment.split("-")[-1]
            else:
                vcode = last_segment

        # Build candidate URLs to test with Video Scraper (player URL first as it is reliable)
        candidates = []
        if vcode:
            candidates.append(f"https://videa.hu/player?v={vcode}")
        if url and url not in candidates:
            candidates.append(url)
        if vcode:
            slug_url = f"https://videa.hu/videok/{vcode}"
            if slug_url not in candidates:
                candidates.append(slug_url)

        headers = {
            "Content-Type": "application/json",
            "User-Agent": USER_AGENT,
        }

        for attempt in range(1, max_retries + 1):
            if cancel_event and cancel_event.is_set():
                raise UploadCancelledException("Feltöltés megszakítva a felhasználó által.")

            for target_url in candidates:
                try:
                    logger.info(f"Calling Video Scraper (attempt {attempt}/{max_retries}) for: {target_url}")
                    response = requests.post(
                        self.endpoint,
                        json={"url": target_url},
                        headers=headers,
                        timeout=DEFAULT_TIMEOUT,
                    )
                    if response.status_code == 200:
                        data = response.json()
                        embed = data.get("embed")
                        if embed and "error" not in embed.lower():
                            logger.info(f"Video Scraper successfully converted {target_url} -> {embed}")
                            return embed
                        else:
                            logger.warning(f"Video Scraper response didn't contain valid embed: {data}")
                    else:
                        logger.warning(f"Video Scraper returned status {response.status_code}: {response.text[:150]}")
                except Exception as e:
                    logger.warning(f"Video Scraper attempt error for {target_url}: {e}")

            if attempt < max_retries:
                logger.info(f"Waiting {retry_delay}s before retrying Video Scraper...")
                if cancel_event:
                    if cancel_event.wait(retry_delay):
                        raise UploadCancelledException("Feltöltés megszakítva a felhasználó által.")
                else:
                    time.sleep(retry_delay)

        # Fallback if Video Scraper is unreachable or failed all retries
        if vcode:
            fallback = f"https://videa.hu/player?v={vcode}"
            logger.warning(f"Video Scraper exhausted retries, using direct player fallback: {fallback}")
            return fallback

        return url
