from __future__ import annotations

from pathlib import Path
import datetime
from html import escape

from openpyxl import load_workbook
from weasyprint import HTML, CSS


XLSX_PATH = Path("/home/fred/Downloads/Definição Ranking_ATUACAPES - Aba1 a Aba4(7).xlsx")
PDF_PATH = Path("/home/fred/projetos/ranking/docs/Criterios_Ranking_Consultores.pdf")
LOGO_PATH = Path("/home/fred/projetos/ranking/docs/assets/logo-capes.png")


def _fmt(cell) -> str:
    if cell is None:
        return ""
    return str(cell).replace("\n", " ").strip()


def _table_html(headers, rows, code_cols=None) -> str:
    code_cols = set(code_cols or [])
    thead = "<tr>" + "".join(f"<th>{escape(_fmt(h))}</th>" for h in headers) + "</tr>"
    body_rows = []
    for row in rows:
        cols = []
        for idx, cell in enumerate(row):
            text = _fmt(cell)
            if idx in code_cols and text:
                text = f"<code>{escape(text)}</code>"
            else:
                text = escape(text)
            cols.append(f"<td>{text}</td>")
        body_rows.append("<tr>" + "".join(cols) + "</tr>")
    tbody = "\n".join(body_rows)
    return f"<table class=\"criteria-table\"><thead>{thead}</thead><tbody>{tbody}</tbody></table>"


def load_planilha() -> dict:
    wb = load_workbook(XLSX_PATH, data_only=True)

    def extract(sheet, header_cols, row_cols, skip_score=False, formula=False):
        ws = wb[sheet]
        headers = [_fmt(c) for c in ws[1][:header_cols]]
        rows = []
        formula_row = ""
        for r in ws.iter_rows(min_row=2, values_only=True):
            if not any(r):
                continue
            if formula and r[0] is None and isinstance(r[1], str) and "tempo =" in r[1]:
                formula_row = r[1]
                continue
            if skip_score and _fmt(r[0]).lower() == "score":
                continue
            rows.append(r[:row_cols])
        return headers, rows, formula_row

    h1, r1, _ = extract("Aba1_Mapa_Atuacoes", 9, 9)
    h2, r2, _ = extract("Aba2_Pontuacao_Base", 4, 4)
    h3, r3, f3 = extract("Aba3_Regras_Tempo", 7, 7, formula=True)
    h4, r4, _ = extract("Aba4_Bonus_Extras", 12, 12)
    h5, r5, _ = extract("Aba5_Detalh. Perfil_Indicadores", 6, 6, skip_score=True)

    return {
        "aba1": {"headers": h1, "rows": r1},
        "aba2": {"headers": h2, "rows": r2},
        "aba3": {"headers": h3, "rows": r3, "formula": f3},
        "aba4": {"headers": h4, "rows": r4},
        "aba5": {"headers": h5, "rows": r5},
    }


def build_html(data: dict) -> str:
    hoje = datetime.date.today().isoformat()
    logo_html = ""
    if LOGO_PATH.exists():
        logo_html = f"<img class=\"cover-logo\" src=\"{LOGO_PATH.as_posix()}\" alt=\"CAPES\" />"

    return f"""
<!doctype html>
<html lang="pt-BR">
<head>
  <meta charset="utf-8" />
  <title>Critérios de Pontuação e Ordenação (Versão Executiva)</title>
  <style>
    @page {{
      size: A4;
      margin: 2.1cm 2.1cm 2.3cm 2.1cm;
    }}
    @page landscape {{
      size: A4 landscape;
      margin: 1.5cm 1.7cm 1.8cm 1.7cm;
    }}
    body {{
      font-family: "Liberation Serif", "Times New Roman", serif;
      color: #0f172a;
      font-size: 11pt;
      line-height: 1.4;
    }}
    h1, h2 {{
      font-family: "Liberation Sans", "Arial", sans-serif;
      color: #0b1f3a;
      margin: 0 0 0.4cm 0;
    }}
    h1 {{
      font-size: 25pt;
      letter-spacing: 0.3px;
    }}
    h2 {{
      font-size: 16pt;
      margin-top: 0;
    }}
    p {{
      margin: 0.3cm 0;
    }}
    .cover {{
      display: flex;
      flex-direction: column;
      justify-content: center;
      align-items: center;
      height: 92vh;
      border: 2px solid #0b1f3a;
      padding: 2.2cm;
      text-align: center;
    }}
    .cover-logo {{
      width: 6.0cm;
      height: auto;
      margin-bottom: 0.7cm;
    }}
    .cover-subtitle {{
      font-size: 14pt;
      color: #1f3b63;
      margin-bottom: 1.1cm;
      max-width: 14cm;
    }}
    .cover-meta {{
      font-size: 10.6pt;
      color: #0f172a;
      border-top: 1px solid #1f3b63;
      padding-top: 0.5cm;
      width: 100%;
      text-align: left;
    }}
    .label {{
      font-weight: 700;
      color: #0b1f3a;
    }}
    section {{
      break-before: page;
    }}
    section.first {{
      break-before: auto;
    }}
    .landscape {{
      page: landscape;
    }}
    table.criteria-table {{
      width: 100%;
      border-collapse: collapse;
      margin: 0.35cm 0 0.5cm 0;
      font-size: 9.3pt;
      table-layout: fixed;
    }}
    table.criteria-table th, table.criteria-table td {{
      border: 1px solid #cbd5f0;
      padding: 5px 6px;
      vertical-align: top;
      word-break: break-word;
      hyphens: auto;
    }}
    table.criteria-table th {{
      background: #eef2ff;
      text-align: left;
      font-weight: 700;
    }}
    table.criteria-table tr:nth-child(even) td {{
      background: #f8fafc;
    }}
    .landscape table.criteria-table {{
      font-size: 8.2pt;
    }}
    .landscape table.criteria-table th,
    .landscape table.criteria-table td {{
      padding: 4px 5px;
    }}
    code {{
      font-family: "Liberation Mono", "Courier New", monospace;
      background: #f1f5f9;
      padding: 0 3px;
      border-radius: 3px;
      font-size: 9.2pt;
    }}
  </style>
</head>
<body>
  <section class="cover">
    {logo_html}
    <h1>Sistema de Ranking de Consultores</h1>
    <div class="cover-subtitle">Critérios de Pontuação e Ordenação (Versão Executiva)</div>
    <div class="cover-meta">
      <div><span class="label">Versão:</span> 1.0</div>
      <div><span class="label">Data:</span> {hoje}</div>
      <div><span class="label">Finalidade:</span> Documento executivo para alta gestão</div>
      <div><span class="label">Escopo:</span> Critérios oficiais do ranking conforme planilha de definição (Abas 1 a 5)</div>
    </div>
  </section>

  <section class="first">
    <h2>Sumário Executivo</h2>
    <p>Este documento consolida, de forma hierárquica e fiel à planilha oficial, todos os critérios utilizados no ranking de consultores. A estrutura está organizada por abas: mapeamento das atuações (Aba 1), pontuação base e tetos (Aba 2), regras de tempo (Aba 3), bônus e selos (Aba 4) e indicadores não pontuáveis (Aba 5).</p>
  </section>

  <section class="landscape">
    <h2>1. Aba 1 — Mapa de Atuações</h2>
    {_table_html(data["aba1"]["headers"], data["aba1"]["rows"], code_cols=[3])}
  </section>

  <section>
    <h2>2. Aba 2 — Pontuação Base e Teto por Atuação</h2>
    {_table_html(data["aba2"]["headers"], data["aba2"]["rows"], code_cols=[0])}
  </section>

  <section>
    <h2>3. Aba 3 — Regras de Tempo</h2>
    {_table_html(data["aba3"]["headers"], data["aba3"]["rows"], code_cols=[0])}
    <p><span class="label">Fórmula da planilha:</span> <code>{escape(_fmt(data["aba3"]["formula"]))}</code></p>
  </section>

  <section class="landscape">
    <h2>4. Aba 4 — Bônus e Selos</h2>
    {_table_html(data["aba4"]["headers"], data["aba4"]["rows"], code_cols=[0])}
  </section>

  <section>
    <h2>5. Aba 5 — Indicadores Não Pontuáveis</h2>
    <p>Os itens abaixo constam na Aba 5 e <strong>não impactam a pontuação</strong>. O indicador <strong>Score</strong> é pontuável e já está coberto pelas regras das Abas 2 a 4.</p>
    {_table_html(data["aba5"]["headers"], data["aba5"]["rows"])}
  </section>

  <section>
    <h2>6. Fonte Oficial</h2>
    <p>Planilha: <code>{escape(str(XLSX_PATH))}</code></p>
  </section>
</body>
</html>
"""


def main() -> None:
    data = load_planilha()
    html = build_html(data)
    HTML(string=html, base_url=str(PDF_PATH.parent)).write_pdf(
        target=str(PDF_PATH),
        stylesheets=[CSS(string="@page { size: A4; }")],
    )
    print(f"PDF: {PDF_PATH}")


if __name__ == "__main__":
    main()
