"""
Stahování zpráv ze všech schránek RBP portálu.

Použij po 01_prihlaseni.py (ten uloží rbp_cookies.json).

POUŽITÍ:
  python 02_stahuj_vse.py
"""

import json
import os
import re
import sys
import time
from datetime import datetime
from pathlib import Path

sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", ".."))
from Knihovny.najdi_dropbox import get_dropbox_root

BASE_URL     = "https://portal.rbp-zp.cz"
INBOX_URL    = f"{BASE_URL}/app/prehled-zprav-ve-schrankach"
DOWNLOAD_URL  = f"{BASE_URL}/html/prehled-zprav-ve-schrankach/zobrazit-prilohu"
PROTOKOL_URL  = f"{BASE_URL}/html/prehled-zprav-ve-schrankach/zobrazit-protokol"

COOKIES_FILE = os.path.abspath(os.path.join(os.path.dirname(__file__), "rbp_cookies.json"))
DOWNLOAD_DIR = os.path.join(get_dropbox_root(), "Ordinace", "Dokumentace_ke_zpracování", "Zúčtovací zprávy", "213 RBP")

SCHRANKY = {
    "31-schranka-vyuctovani":                        "Schránka vyúčtování",
    "22-schranka-pzs":                               "Schránka PZS",
    "24-schranka-klienta":                           "Schránka klienta",
    "135-prohlizeni-klientely-odbornosti-001":       "Prohlížení klientely",
    "136-prohlizeni-plateb":                         "Prohlížení plateb",
    "138-zadanka-o-schvaleni":                       "Žádanka o schválení",
    "170-schranka-poskytovatele-zdravotnich-sluzeb": "Schránka poskytovatele ZS",
    "182-schranka-klientu-portalu":                  "Schránka klientů portálu",
    "203-vypis-pojistencu-registrovanych-u-pzs":     "Výpis pojištěnců reg. u PZS",
    "241-smluvni-dokumenty-pro-pzs":                 "Smluvní dokumenty pro PZS",
}


def make_session():
    try:
        import requests
    except ImportError:
        print("Chybi requests: pip install requests")
        sys.exit(1)
    import requests as req

    if not os.path.exists(COOKIES_FILE):
        print(f"Soubor {COOKIES_FILE} nenalezen - spust 01_prihlaseni.py")
        sys.exit(1)

    with open(COOKIES_FILE, encoding="utf-8") as f:
        cookies = json.load(f)

    s = req.Session()
    s.headers["User-Agent"] = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36"
    for c in cookies:
        s.cookies.set(c["name"], c["value"], domain=c["domain"].lstrip("."))

    r = s.get(INBOX_URL, timeout=15)
    if "prihlaseni" in r.url or "login" in r.url.lower():
        print("Cookies expirovala - spust 01_prihlaseni.py")
        sys.exit(1)
    print(f"Prihlaseni OK ({r.url})")
    return s


def parse_date(date_str: str) -> str:
    try:
        return datetime.strptime(date_str.strip()[:19], "%d.%m.%Y %H:%M:%S").strftime("%Y-%m-%d")
    except Exception:
        try:
            return datetime.strptime(date_str.strip()[:10], "%d.%m.%Y").strftime("%Y-%m-%d")
        except Exception:
            return "0000-00-00"


def safe_filename(name: str) -> str:
    return re.sub(r'[\\/:*?"<>|]', "_", name).strip()


def parse_row(cells: list) -> dict:
    date_raw  = cells[1].strip() if len(cells) > 1 else ""
    desc_raw  = cells[2].strip() if len(cells) > 2 else ""
    fname_raw = cells[3].strip() if len(cells) > 3 else ""

    desc_lines = [l.strip() for l in desc_raw.split("\n") if l.strip()]
    if len(desc_lines) >= 3:
        description = desc_lines[2]
    elif len(desc_lines) >= 2:
        description = desc_lines[1]
    else:
        description = desc_lines[0] if desc_lines else ""
    description = description[:80]

    fname_match = re.match(r'^(.+?)\s*\(\d{2}\.\d{2}\.\d{4}\)\s*$', fname_raw)
    original = fname_match.group(1).strip() if fname_match else fname_raw.split("(")[0].strip()
    orig_path = Path(original)
    stem = orig_path.stem or "zprava"
    ext  = orig_path.suffix or ""

    date_iso = parse_date(date_raw)
    name = f"{date_iso} {safe_filename(description)} ({safe_filename(stem)}){ext}"
    if len(name) > 240:
        name = f"{date_iso} ({safe_filename(stem)}){ext}"

    return {"date": date_iso, "desc": description, "original": original, "filename": name}


def process_schránka(page, context, segment: str, name: str, already: set) -> tuple:
    downloaded = 0
    skipped = 0
    page_num = 1
    seen_ids: set = set()

    while True:
        url = f"{INBOX_URL}/{segment}/stranka-{page_num}"
        print(f"  Stranka {page_num}: {url}")
        try:
            page.goto(url, wait_until="domcontentloaded", timeout=30_000)
        except Exception as e:
            print(f"  Navigace selhala: {e}")
            break

        page.wait_for_load_state("networkidle", timeout=15_000)

        data = page.evaluate("""() => {
            const rows = [];
            for (const tr of document.querySelectorAll('table tr')) {
                const cells = Array.from(tr.querySelectorAll('td')).map(td => td.innerText.trim());
                if (cells.length < 4) continue;
                const dlLink = tr.querySelector('a[onclick*="SchrPolOpenFile"]');
                if (!dlLink) continue;
                const mFile = dlLink.getAttribute('onclick').match(/\\d+/);
                const protLink = tr.querySelector('a[onclick*="SchrPolDBProtokol"]');
                const mProt = protLink ? protLink.getAttribute('onclick').match(/\\d+/) : null;
                rows.push({
                    cells,
                    fileId:    mFile ? mFile[0] : null,
                    protokolId: mProt ? mProt[0] : null,
                });
            }
            return rows;
        }""")
        rows = [r for r in data if r["fileId"]]

        if not rows:
            print(f"  Stranka {page_num} - zadne radky, koncim schranku.")
            break

        current_ids = {r["fileId"] for r in rows}
        if current_ids & seen_ids:
            print(f"  Stranka {page_num} - opakujici se obsah, koncim schranku.")
            break
        seen_ids.update(current_ids)

        print(f"  Nalezeno {len(rows)} zprav.")

        for row in rows:
            info = parse_row(row["cells"])
            target = os.path.join(DOWNLOAD_DIR, info["filename"])

            # Stáhni přílohu (pokud ještě neexistuje)
            if info["filename"] in already or os.path.exists(target):
                skipped += 1
            else:
                dl_url = f"{DOWNLOAD_URL}?zprava_id={row['fileId']}"
                try:
                    r = context.request.get(dl_url, headers={"Referer": INBOX_URL}, timeout=30_000)
                    if not r.ok:
                        print(f"    HTTP {r.status} priloha (id={row['fileId']})")
                    else:
                        with open(target, "wb") as f:
                            f.write(r.body())
                        print(f"    OK: {info['filename']}")
                        already.add(info["filename"])
                        downloaded += 1
                except Exception as e:
                    print(f"    Chyba priloha (id={row['fileId']}): {e}")
                time.sleep(1.0)

            # Stáhni protokol (podání) — vždy nezávisle na příloze
            if row.get("protokolId"):
                prot_name = safe_filename(f"{info['date']} {info['desc']} (protokol-{row['protokolId']}).html")
                prot_target = os.path.join(DOWNLOAD_DIR, prot_name)
                if prot_name not in already and not os.path.exists(prot_target):
                    prot_url = f"{PROTOKOL_URL}?id={row['protokolId']}"
                    try:
                        r2 = context.request.get(prot_url, headers={"Referer": INBOX_URL}, timeout=30_000)
                        if r2.ok:
                            with open(prot_target, "wb") as f:
                                f.write(r2.body())
                            print(f"    OK: {prot_name}")
                            already.add(prot_name)
                            downloaded += 1
                        else:
                            print(f"    HTTP {r2.status} protokol (id={row['protokolId']})")
                    except Exception as e:
                        print(f"    Chyba protokol (id={row['protokolId']}): {e}")
                    time.sleep(1.0)

        page_num += 1

    return downloaded, skipped


def main() -> None:
    try:
        from playwright.sync_api import sync_playwright
    except ImportError:
        print("Chybi playwright: pip install playwright && playwright install chrome")
        sys.exit(1)

    os.makedirs(DOWNLOAD_DIR, exist_ok=True)

    with open(COOKIES_FILE, encoding="utf-8") as f:
        cookies = json.load(f)

    with sync_playwright() as p:
        context = p.chromium.launch_persistent_context(
            user_data_dir=os.path.join(os.path.dirname(__file__), "chrome_profile"),
            channel="chrome",
            headless=False,
            slow_mo=100,
            ignore_https_errors=True,
        )
        try:
            context.add_cookies(cookies)
            page = context.new_page()
            page.goto(INBOX_URL, wait_until="domcontentloaded", timeout=30_000)

            if "prihlaseni" in page.url or "login" in page.url.lower():
                print("Cookies expirovala - spust 01_prihlaseni.py")
                return
            print(f"Prihlaseni OK\n")

            already = set(os.listdir(DOWNLOAD_DIR))
            print(f"V archivu: {len(already)} souboru.\n")

            total_dl = total_skip = 0
            for segment, name in SCHRANKY.items():
                print(f"\n=== {name} ===")
                dl, sk = process_schránka(page, context, segment, name, already)
                print(f"  {name}: stazeno {dl}, preskoceno {sk}")
                total_dl += dl
                total_skip += sk

            print(f"\nHotovo. Celkem stazeno: {total_dl}, preskoceno: {total_skip}")

        finally:
            context.close()


if __name__ == "__main__":
    main()
