# -*- coding: utf-8 -*-
"""
Jeden generátor → dva JSON soubory:
 - streaming_top10.json (TOP 10 Movies/TV Shows pro každou platformu)
 - streaming_calendar.json (kalendář)

Bez externích knihoven (BeautifulSoup/requests). Používá urllib + regex + HTMLParser (jen pro kalendář).
TOP10 se detekuje podle textové hlavičky „TOP Movies …“ / „TOP TV Shows …“ a bere nejbližší následující <table>.
Anchor filtrace: jen href obsahující „/title/“.
"""

import urllib.request
import re
import json
import datetime
from html.parser import HTMLParser

from resources.lib.utils.log_utils import get_logger

log = get_logger()

PLATFORMS = {
    'Netflix': 'https://flixpatrol.com/top10/netflix/',
    'HBO Max': 'https://flixpatrol.com/top10/hbo-max/',
    'Disney+': 'https://flixpatrol.com/top10/disney/',
    'Prime Video': 'https://flixpatrol.com/top10/amazon-prime/',
    'Apple TV+': 'https://flixpatrol.com/top10/apple-tv/',
    'Paramount+': 'https://flixpatrol.com/top10/paramount-plus/',
}

UA = 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/115 Safari/537.36'


def fetch_html(url: str) -> str:
    """Stáhne HTML s UA; vrací prázdný řetězec při chybě."""
    try:
        req = urllib.request.Request(url, headers={'User-Agent': UA})
        with urllib.request.urlopen(req, timeout=25) as resp:
            return resp.read().decode('utf-8', errors='replace')
    except Exception as e:
        log.error(f"Chyba při načítání {url}: {e}")
        return ""


def _strip_tags(text: str) -> str:
    """Odstraní vnitřní HTML tagy z textu anchoru."""
    return re.sub(r'<[^>]+>', '', text or '')


def _sanitize_title(t: str) -> str:
    """Vyčistí nechtěné znaky a whitespace."""
    t = (t or "").strip()
    for ch in ('↗', '↘', '▲', '▼', '•'):
        t = t.replace(ch, '')
    return ' '.join(t.split())


def _extract_table_after_heading(html: str, heading_regex: str) -> str:
    """
    Najde blok s hlavičkou (např. 'TOP Movies') a vybere nejbližší následující <table>…</table>.
    Vrací HTML téhle tabulky (string) nebo ''.
    """
    # Najdi pozici hlavičky
    m_head = re.search(heading_regex, html, flags=re.IGNORECASE | re.DOTALL)
    if not m_head:
        return ""
    start = m_head.end()
    # Po hlavičce hledej první tabulku (non-greedy)
    m_table = re.search(r'<table\b[\s\S]*?</table>', html[start:], flags=re.IGNORECASE | re.DOTALL)
    return m_table.group(0) if m_table else ""


def _extract_titles_from_table(table_html: str) -> list:
    """
    Z <table> vyextrahuje tituly: vezme <tbody> a z něj všechny <a> s href obsahujícím '/title/'.
    Vrátí list textů (max 10, bez duplicit).
    """
    if not table_html:
        return []

    # Vezmi tbody část (většinou jediná)
    m_tbody = re.search(r'<tbody\b[\s\S]*?</tbody>', table_html, flags=re.IGNORECASE | re.DOTALL)
    tbody_html = m_tbody.group(0) if m_tbody else table_html  # fallback: celá tabulka

    # Najdi anchor s href + vnitřní text
    anchors = re.findall(r'<a[^>]+href="([^"]+)"[^>]*>([\s\S]*?)</a>', tbody_html, flags=re.IGNORECASE | re.DOTALL)
    titles = []
    seen = set()

    for href, inner in anchors:
        href_l = (href or '').lower()
        if '/title/' not in href_l:
            continue  # ignoruj odkazy, které nevedou na stránku titulu
        title = _sanitize_title(_strip_tags(inner))
        if not title or len(title) < 2:
            continue
        if title in seen:
            continue
        seen.add(title)
        titles.append(title)
        if len(titles) >= 10:
            break

    return titles


def fetch_platform_top10(url: str) -> dict:
    """
    Vrátí {'Movies': [...], 'TV Shows': [...]} rozpoznané pomocí hlavičky stránky,
    ignoruje „by country“ (protože hledáme explicitně 'TOP Movies' / 'TOP TV Shows').
    """
    html = fetch_html(url)
    if not html:
        return {"Movies": [], "TV Shows": []}

    # Najdi tabulku pro Movies
    movies_table = _extract_table_after_heading(html, r'TOP\s+Movies\b[\s\S]*?on\b')
    movies = _extract_titles_from_table(movies_table)

    # Najdi tabulku pro TV Shows
    shows_table = _extract_table_after_heading(html, r'TOP\s+TV\s+Shows\b[\s\S]*?on\b')
    tvshows = _extract_titles_from_table(shows_table)

    return {"Movies": movies[:10], "TV Shows": tvshows[:10]}


# ---------- Kalendář (základní parser HTMLParser; zatím ponechán) ----------
class CalendarParser(HTMLParser):
    def __init__(self):
        super().__init__()
        self.in_td = False
        self.current_row = []
        self.rows = []

    def handle_starttag(self, tag, attrs):
        if tag == 'tr':
            self.current_row = []
        elif tag == 'td':
            self.in_td = True
            self._td_buf = []

    def handle_endtag(self, tag):
        if tag == 'td':
            self.in_td = False
            text = _sanitize_title(''.join(self._td_buf))
            self.current_row.append(text)
            self._td_buf = []
        elif tag == 'tr':
            if self.current_row:
                self.rows.append(self.current_row)

    def handle_data(self, data):
        if self.in_td:
            self._td_buf.append(data or '')


def fetch_calendar_events() -> list:
    html = fetch_html("https://flixpatrol.com/calendar/")
    if not html:
        return []
    parser = CalendarParser()
    parser.feed(html)
    rows = parser.rows
    # Přeskoč hlavičku, pokud první buňka obsahuje 'date'
    if rows and rows[0] and 'date' in (rows[0][0] or '').lower():
        rows = rows[1:]
    events = []
    for cols in rows:
        if len(cols) >= 5:
            events.append({
                "release_date": cols[0],
                "title": cols[1],
                "type": cols[2],
                "country": cols[3],
                "platform": cols[4],
                "genres": cols[5:] if len(cols) > 5 else []
            })
    return events


# ---------- Veřejné API generátoru ----------
def generate_top10(output_path: str) -> dict:
    top10_data = {}
    for name, url in PLATFORMS.items():
        top10_data[name] = fetch_platform_top10(url)
    out = {"date": datetime.datetime.now().strftime("%Y-%m-%d"), "top10": top10_data}
    with open(output_path, "w", encoding="utf-8") as f:
        json.dump(out, f, indent=4, ensure_ascii=False)
    return out


def generate_calendar(output_path: str) -> dict:
    calendar_data = fetch_calendar_events()
    out = {"date": datetime.datetime.now().strftime("%Y-%m-%d"), "calendar": calendar_data}
    with open(output_path, "w", encoding="utf-8") as f:
        json.dump(out, f, indent=4, ensure_ascii=False)
    return out


def generate_all(top10_path: str, calendar_path: str) -> None:
    generate_top10(top10_path)
    generate_calendar(calendar_path)