# -*- coding: utf-8 -*-
"""BÁO CÁO HTML MUA HÀNG — đọc TRỰC TIẾP từ BẢNG TÍNH Excel đã làm sạch.

Nguyên tắc (chốt 14/09/2026):
  * Nguồn dữ liệu = bảng tính Excel `MUA_HANG_*_DA-LAM-SACH_SO-SANH.xlsx` (KHÔNG qua DOCX trung gian).
  * Tự nhận diện số kỳ: các cột "Tháng NN 2026 (Khối lượng Kg)" + cột kỳ đang chạy "Từ 1->N Tháng MM 2026".
  * Số ngày mỗi kỳ: theo tháng dương lịch (2026: T2=28); kỳ đang chạy lấy N từ header.
  * Gắn NHÀ MÁY cho từng khách: join bảng `nha_may_alias` trong CSDL btchem.db (CRMG = Trendworld; mọi cách viết
    sai như Trendwood/Trenwood/TRENWORD đều quy về Trendworld).

Dùng:  python build_muahang_portal.py <file.xlsx> [--out <file.html>]
"""
import os, re, sys, json, sqlite3, argparse
import openpyxl

DBP = r"C:\c\deepseek-harness\claw2-db\btchem.db"
NGAY_THANG = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]   # 2026 không nhuận


def num(v):
    if v is None:
        return None
    if isinstance(v, (int, float)):
        return float(v)
    s = str(v).strip().replace(",", "").replace("+", "").replace("%", "")
    if s in ("", "-", "—"):
        return None
    try:
        return float(s)
    except ValueError:
        return None


def parse_header(hdr):
    """Trả về (cot_ky, ngay_ky, cot_tb_truoc, cot_tb_ky, cot_chenh, cot_pct)."""
    cot_ky, ngay_ky = [], []
    ct, ctt, ctk, cc, cp = None, None, None, None, None
    for i, h in enumerate(hdr):
        t = str(h or "").strip()
        m = re.match(r"Tháng\s*(\d{1,2})\s*\d{0,4}\s*\(Kh", t, re.I)
        if m:
            thang = int(m.group(1))
            cot_ky.append(i); ngay_ky.append(NGAY_THANG[thang - 1])
            continue
        m = re.match(r"Từ\s*1\s*->\s*(\d+)\s*Tháng\s*(\d{1,2})", t, re.I)
        if m:
            cot_ky.append(i); ngay_ky.append(int(m.group(1)))
            continue
        if re.match(r"TB Ngày Tháng Trước", t, re.I): ct = i
        elif re.match(r"TB Ngày Tháng", t, re.I): ctk = i
        elif re.match(r"Chênh Lệch \(Kg", t, re.I): cc = i
        elif re.match(r"Chênh Lệch \(%\)", t, re.I): cp = i
    return cot_ky, ngay_ky, ct, ctk, cc, cp


def load(path):
    ws = openpyxl.load_workbook(path, data_only=True).worksheets[0]
    rows = list(ws.iter_rows(values_only=True))
    hi = next(i for i, r in enumerate(rows) if r and str(r[0] or "").strip().lower() == "stt")
    hdr = rows[hi]
    cot_ky, ngay_ky, ct, ctk, cc, cp = parse_header(hdr)
    nky = len(cot_ky)
    thang_ky = int((re.search(r"Tháng\s*(\d{1,2})", str(hdr[cot_ky[-1]])) or [0, 0])[1]) or 9

    kh, tot = [], None
    for r in rows[hi + 1:]:
        ma, ten = str(r[1] or "").strip(), str(r[2] or "").strip()
        if ten.upper().startswith("TỔNG CỘNG"):
            tot = r; continue
        if not ma or not ten:
            continue
        tong = [num(r[c]) or 0 for c in cot_ky]
        tb = []
        for i, c in enumerate(cot_ky):
            if i == nky - 1 and ctk is not None:
                tb.append(num(r[ctk]) or (round(tong[i] / ngay_ky[i], 1) if ngay_ky[i] else 0))
            else:
                tb.append(round(tong[i] / ngay_ky[i], 1) if ngay_ky[i] and tong[i] else 0)
        pct = (num(r[cp]) or 0) * 100 if cp is not None and not str(r[cp] or "").endswith("%") else (num(r[cp]) or 0)
        kh.append(dict(stt=int(ma and r[0] or len(kh) + 1), ma=ma, ten=ten, tb=tb,
                       chenh=num(r[cc]) or 0 if cc is not None else 0, pct=pct))
    if tot is None:
        raise SystemExit("Không tìm thấy dòng Tổng cộng trong bảng tính")
    tong_arr = [num(tot[c]) or 0 for c in cot_ky]
    tb_arr = [round(tong_arr[i] / ngay_ky[i], 0) if ngay_ky[i] else 0 for i in range(nky)]
    return kh, tong_arr, ngay_ky, tb_arr, thang_ky, nky


def gan_nha_may(kh):
    """Gắn tên nhà máy cho khách: khớp mã KH hoặc tên pháp nhân với bảng alias (1 nguồn duy nhất)."""
    try:
        c = sqlite3.connect(f"file:{DBP}?mode=ro", uri=True)
        ten_nm = {r[0]: r[1] for r in c.execute("SELECT id, ten FROM nha_may")}
        als = list(c.execute("SELECT nha_may_id, alias FROM nha_may_alias"))
        c.close()
    except Exception as e:
        print("! Không đọc được CSDL để gắn nhà máy:", e)
        return 0
    n = 0
    for k in kh:
        up = k["ten"].upper()
        for nid, al in als:
            a = (al or "").strip().upper()
            if len(a) < 4:
                continue
            if a == k["ma"].upper() or (len(a) >= 8 and a in up):
                k["nm"] = ten_nm.get(nid, "")
                n += 1
                break
    return n


def build(src, out):
    kh, tong_arr, ngay_arr, tb_arr, thang_ky, nky = load(src)
    n_nm = gan_nha_may(kh)
    n_tang = sum(1 for k in kh if k["chenh"] > 0)
    n_giam = sum(1 for k in kh if k["chenh"] < 0)
    n_dung = sum(1 for k in kh if k["chenh"] == 0)
    ch = tb_arr[-1] - tb_arr[-2]
    pct = (ch / tb_arr[-2] * 100) if tb_arr[-2] else 0
    MONTHS = [f"T{i+1}" for i in range(nky - 1)] + [f"T{thang_ky} ({ngay_arr[-1]} ngày)"]
    KY = f"Kỳ T{thang_ky} (1-{ngay_arr[-1]}): 01/{thang_ky:02d} → {ngay_arr[-1]:02d}/{thang_ky:02d}/2026"

    html = TEMPLATE
    html = html.replace("__KY__", KY)
    html = html.replace("__KY_RANGE__", f"01/{thang_ky:02d} → {ngay_arr[-1]:02d}/{thang_ky:02d}/2026")
    html = html.replace("__KY_NGAY__", str(ngay_arr[-1]))
    html = html.replace("__N_KH__", str(len(kh)))
    html = html.replace("__TONG_LAST__", f"{tong_arr[-1]:,.0f}")
    html = html.replace("__TB_LAST__", f"{tb_arr[-1]:,.0f}")
    html = html.replace("__CHENH__", f"{ch:+,.0f} ({pct:+.1f}%)")
    html = html.replace("__CHENH_PCT__", f"{pct:+.1f}%")
    html = html.replace("__N_TANG__", str(n_tang))
    html = html.replace("__N_GIAM__", str(n_giam))
    html = html.replace("__N_DUNG__", str(n_dung))
    html = html.replace("__KH__", json.dumps(kh, ensure_ascii=False))
    html = html.replace("__DAYS__", json.dumps(ngay_arr))
    html = html.replace("__MONTHS__", json.dumps(MONTHS, ensure_ascii=False))
    html = html.replace("__TONG__", json.dumps(tong_arr))
    html = html.replace("__TBARR__", json.dumps(tb_arr))
    with open(out, "w", encoding="utf-8") as f:
        f.write(html)
    return dict(kh=len(kh), nha_may=n_nm, tong=tong_arr[-1], tb=tb_arr[-1], ch=ch, pct=pct,
                ky=KY, out=out, size=len(html), ngay=ngay_arr[-1])


TEMPLATE = r'''<!DOCTYPE html>
<html lang="vi">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Báo cáo Mua hàng — Tháng 9/2026 (Kỳ T9) | BT Chem</title>
<style>
:root{
  --xanh:#1F3A5F; --xanh2:#2E5E9E; --do:#C00000; --vang:#E6A817; --xanhla:#1E7D32;
  --xam:#f4f6f9; --xam2:#e9edf3; --den:#1a1a1a; --trang:#fff; --tim:#6a3fc0;
}
*{box-sizing:border-box;margin:0;padding:0}
body{font-family:'Segoe UI',Tahoma,Arial,sans-serif;background:var(--xam);color:var(--den);font-size:14px;line-height:1.5}
.wrap{max-width:1320px;margin:0 auto;padding:0 16px}

/* ===== HEADER ===== */
header{background:linear-gradient(135deg,var(--xanh) 0%,var(--xanh2) 100%);color:#fff;padding:26px 0 18px;box-shadow:0 3px 12px rgba(0,0,0,.18)}
header .wrap{display:flex;flex-wrap:wrap;align-items:center;gap:16px;justify-content:space-between}
.logo h1{font-size:22px;font-weight:700;letter-spacing:.3px}
.logo p{font-size:12.5px;opacity:.92;margin-top:3px}
.kpi{display:flex;gap:10px;flex-wrap:wrap}
.kpi .box{background:rgba(255,255,255,.14);border:1px solid rgba(255,255,255,.28);border-radius:10px;padding:8px 16px;text-align:center;min-width:96px}
.kpi .box b{display:block;font-size:20px;line-height:1.2}
.kpi .box span{font-size:10.5px;opacity:.9;text-transform:uppercase;letter-spacing:.5px}

/* ===== NAV ===== */
nav{background:var(--xanh);border-top:1px solid rgba(255,255,255,.15)}
nav .wrap{display:flex;gap:4px;flex-wrap:wrap}
nav button{background:transparent;color:#cfd8e8;border:none;padding:12px 18px;font-size:14px;cursor:pointer;border-bottom:3px solid transparent;font-weight:600;transition:.15s}
nav button:hover{color:#fff;background:rgba(255,255,255,.08)}
nav button.on{color:#fff;border-bottom-color:var(--vang);background:rgba(255,255,255,.10)}

/* ===== SECTIONS ===== */
section{display:none;padding:22px 0 40px}
section.on{display:block}
h2.sec{font-size:19px;color:var(--xanh);margin:6px 0 4px;border-left:5px solid var(--do);padding-left:10px}
p.sub{color:#5a6472;font-size:12.5px;margin-bottom:14px}

/* ===== CARDS ===== */
.cards{display:grid;grid-template-columns:repeat(auto-fit,minmax(200px,1fr));gap:12px;margin:14px 0}
.card{background:#fff;border-radius:12px;padding:14px 16px;box-shadow:0 1px 4px rgba(0,0,0,.08);border-top:4px solid var(--xanh2)}
.card b{font-size:26px;display:block;color:var(--xanh)}
.card span{font-size:12px;color:#5a6472}
.card.red{border-top-color:var(--do)} .card.green{border-top-color:var(--xanhla)} .card.yellow{border-top-color:var(--vang)}

/* ===== CHART ===== */
.chart-box{background:#fff;border-radius:12px;padding:16px;box-shadow:0 1px 4px rgba(0,0,0,.08);margin:12px 0}
.chart-box h3{font-size:14.5px;color:var(--xanh);margin-bottom:12px}
.bar-row{display:flex;align-items:center;gap:8px;margin:5px 0}
.bar-row .lbl{width:220px;font-size:12px;text-align:right;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.bar-row .track{flex:1;background:var(--xam2);border-radius:6px;height:22px;position:relative;overflow:hidden}
.bar-row .fill{height:100%;border-radius:6px;background:linear-gradient(90deg,var(--xanh2),#4a8ad4);display:flex;align-items:center;justify-content:flex-end;padding-right:8px;color:#fff;font-size:11px;font-weight:700;min-width:34px;white-space:nowrap;transition:width .5s}
.bar-row .fill.red{background:linear-gradient(90deg,var(--do),#e04545)}
.bar-row .fill.green{background:linear-gradient(90deg,var(--xanhla),#35a54e)}
.bar-row .val{width:70px;font-size:12px;font-weight:700;color:var(--xanh)}
.legend{display:flex;gap:14px;flex-wrap:wrap;font-size:12px;margin-top:8px}
.legend i{display:inline-block;width:12px;height:12px;border-radius:3px;margin-right:4px;vertical-align:-1px}

/* ===== TABLE ===== */
.controls{background:#fff;border-radius:12px;padding:12px 14px;box-shadow:0 1px 4px rgba(0,0,0,.08);margin:12px 0;display:flex;gap:10px;flex-wrap:wrap;align-items:center}
.controls input[type=text]{flex:1;min-width:180px;padding:8px 12px;border:1px solid #c9d2dd;border-radius:8px;font-size:13px}
.controls select{padding:8px 10px;border:1px solid #c9d2dd;border-radius:8px;font-size:13px;background:#fff}
.controls label{font-size:12px;color:#5a6472}
.tbl-wrap{background:#fff;border-radius:12px;box-shadow:0 1px 4px rgba(0,0,0,.08);overflow:auto;max-height:640px}
table{border-collapse:collapse;width:100%;font-size:12.5px;min-width:1180px}
thead th{position:sticky;top:0;background:var(--xanh);color:#fff;padding:9px 10px;text-align:left;cursor:pointer;user-select:none;white-space:nowrap;z-index:2}
thead th:hover{background:var(--xanh2)}
thead th.asc::after{content:' ▲';font-size:10px}
thead th.desc::after{content:' ▼';font-size:10px}
tbody td{padding:7px 10px;border-bottom:1px solid #e7ebf1;vertical-align:top}
tbody tr:nth-child(even){background:#f8fafc}
tbody tr:hover{background:#eef4fb}
td.num{text-align:right;font-variant-numeric:tabular-nums;white-space:nowrap}
.pill{display:inline-block;padding:2px 9px;border-radius:20px;font-size:11px;font-weight:700;white-space:nowrap}
.pill.duong{background:#e8f5e9;color:var(--xanhla)}
.pill.do{background:#fdecea;color:var(--do)}
.pill.xam{background:#eef0f3;color:#5a6472}
.hint{font-size:11.5px;color:#7b8494;margin-top:6px;font-style:italic}
.diff-up{color:var(--xanhla);font-weight:700}
.diff-down{color:var(--do);font-weight:700}
.diff-zero{color:#7b8494}

footer{background:var(--xanh);color:#c9d4e4;padding:18px 0;text-align:center;font-size:12px;margin-top:30px}
.src{font-size:11px;color:#8a94a6;margin-top:4px}
@media(max-width:768px){.bar-row .lbl{width:130px}.kpi .box{min-width:78px}.kpi .box b{font-size:16px}}
</style>
</head>
<body>

<header>
  <div class="wrap">
    <div class="logo">
      <h1>🛒 BÁO CÁO MUA HÀNG — THÁNG 9/2026</h1>
      <p>CÔNG TY TNHH SX–TM HÓA KEO BÌNH THẠNH · PHÒNG KINH DOANH · <b>__KY__</b></p>
    </div>
    <div class="kpi">
      <div class="box"><b>__N_KH__</b><span>Khách hàng mua</span></div>
      <div class="box"><b>__TONG_LAST__</b><span>Tổng Kg Kỳ T9</span></div>
      <div class="box"><b>__TB_LAST__</b><span>TB/ngày Kỳ T9</span></div>
      <div class="box"><b>__CHENH__</b><span>vs Tháng 8</span></div>
    </div>
  </div>
</header>

<nav>
  <div class="wrap">
    <button class="on" data-tab="tongquan">🏠 Tổng quan</button>
    <button data-tab="chitiet">🏭 Chi tiết khách hàng</button>
    <button data-tab="top">📈 Top tăng / giảm</button>
    <button data-tab="sosanh">⚖️ So sánh khách hàng</button>
  </div>
</nav>

<div class="wrap">

<!-- ==================== TỔNG QUAN ==================== -->
<section id="tongquan" class="on">
  <h2 class="sec">Tổng quan toàn công ty — 8 tháng đầu năm + Kỳ T9 (__KY_RANGE__)</h2>
  <p class="sub">Lượng bán trung bình ngày (Kg/ngày) quy đổi từ tổng sản lượng mua hàng theo số ngày thực tế từng kỳ. Kỳ T9 = __TB_LAST__ Kg/ngày (__CHENH_PCT__ so với Tháng 8).</p>

  <div class="cards">
    <div class="card"><b>__TB_LAST__</b><span>TB/ngày Kỳ T9 (__KY_NGAY__ ngày)</span></div>
    <div class="card green"><b>__N_TANG__</b><span>KH tăng so với T8</span></div>
    <div class="card red"><b>__N_GIAM__</b><span>KH giảm so với T8</span></div>
    <div class="card yellow"><b>__N_DUNG__</b><span>KH không đổi</span></div>
  </div>

  <div class="chart-box">
    <h3>📊 Tổng sản lượng (Kg) theo kỳ</h3>
    <div id="chartTong"></div>
  </div>

  <div class="chart-box">
    <h3>📈 Lượng bán trung bình ngày (Kg/ngày) theo kỳ</h3>
    <div id="chartTB"></div>
  </div>

  <div class="chart-box">
    <h3>🏆 Top 15 khách hàng theo TB/ngày Kỳ T9 (Kg/ngày)</h3>
    <div id="chartTop"></div>
    <div class="legend"><span><i style="background:var(--xanhla)"></i>Tăng so T8</span><span><i style="background:var(--do)"></i>Giảm so T8</span></div>
  </div>
</section>

<!-- ==================== CHI TIẾT ==================== -->
<section id="chitiet">
  <h2 class="sec">Chi tiết từng khách hàng (__N_KH__ KH)</h2>
  <p class="sub">Bấm tiêu đề cột để sắp xếp. Chênh lệch = TB/ngày Kỳ T9 so với Tháng 8.</p>
  <div class="controls">
    <input type="text" id="khSearch" placeholder="🔍 Tìm mã KH, tên khách hàng...">
    <select id="khTrend"><option value="">Tất cả xu hướng</option><option value="up">📈 Tăng</option><option value="down">📉 Giảm</option><option value="flat">➖ Không đổi</option></select>
    <select id="khMin"><option value="0">Tất cả TB/ngày</option><option value="100">≥ 100 Kg/ngày</option><option value="300">≥ 300 Kg/ngày</option><option value="500">≥ 500 Kg/ngày</option><option value="1000">≥ 1.000 Kg/ngày</option></select>
    <button id="khReset" style="border:none;padding:9px 16px;border-radius:8px;font-size:13px;font-weight:700;cursor:pointer;background:#fff;border:1.5px solid var(--xanh);color:var(--xanh)">⟲ Reset</button>
  </div>
  <div class="tbl-wrap">
    <table id="khTable">
      <thead><tr>
        <th data-k="stt">STT</th><th data-k="ma">Mã KH</th><th data-k="ten">Tên khách hàng</th>
        <th data-k="nm">Nhà máy</th>
        <th data-k="t0" class="num">TB T1</th><th data-k="t1" class="num">TB T2</th><th data-k="t2" class="num">TB T3</th>
        <th data-k="t3" class="num">TB T4</th><th data-k="t4" class="num">TB T5</th><th data-k="t5" class="num">TB T6</th>
        <th data-k="t6" class="num">TB T7</th><th data-k="t7" class="num">TB T8</th><th data-k="t8" class="num">TB T9</th>
        <th data-k="chenh" class="num">Chênh lệch</th><th data-k="pct" class="num">%</th>
      </tr></thead>
      <tbody></tbody>
    </table>
  </div>
  <p class="hint" id="khCount"></p>
</section>

<!-- ==================== TOP TĂNG/GIẢM ==================== -->
<section id="top">
  <h2 class="sec">Top khách hàng tăng / giảm mạnh nhất (Kỳ T9 vs Tháng 8)</h2>
  <p class="sub">Theo chênh lệch TB/ngày tuyệt đối (Kg/ngày).</p>

  <div style="display:grid;grid-template-columns:repeat(auto-fit,minmax(320px,1fr));gap:16px">
    <div class="chart-box">
      <h3 style="color:var(--xanhla)">🚀 Top 10 khách hàng tăng mạnh nhất</h3>
      <div id="topUp"></div>
    </div>
    <div class="chart-box">
      <h3 style="color:var(--do)">🔻 Top 10 khách hàng sụt giảm nhiều nhất</h3>
      <div id="topDown"></div>
    </div>
  </div>
</section>

<!-- ==================== SO SÁNH ==================== -->
<section id="sosanh">
  <h2 class="sec">So sánh trực tiếp 2 khách hàng</h2>
  <p class="sub">Đối chiếu xu hướng sản lượng trung bình ngày qua các kỳ giữa 2 đơn vị.</p>
  <div class="controls">
    <label>Khách hàng A:</label>
    <select id="cmpA"><option value="">-- Chọn khách hàng A --</option></select>
    <label>Khách hàng B:</label>
    <select id="cmpB"><option value="">-- Chọn khách hàng B --</option></select>
    <button id="cmpGo" style="border:none;padding:9px 18px;border-radius:8px;font-size:13px;font-weight:700;cursor:pointer;background:var(--xanh);color:#fff">Đối chiếu</button>
  </div>
  <div id="cmpResult" style="display:none;margin-top:14px"></div>
</section>

</div>

<footer>
  <div class="wrap">
    <p><b>BÁO CÁO PHÂN TÍCH MUA HÀNG — CÔNG TY TNHH SX–TM HÓA KEO BÌNH THẠNH</b></p>
    <p class="src">Nguồn dữ liệu: BAO_CAO_SO_SANH_MUA_HANG_T9.docx · Cập nhật tự động ngày 14/09/2026</p>
  </div>
</footer>

<script>
const KH = __KH__;
const MONTHS = __MONTHS__;
const TONG = __TONG__;
const TBARR = __TBARR__;
const DAYS = __DAYS__;

const num = n => n == null ? '-' : Number(n).toLocaleString('vi-VN');
const fmtPct = p => (p>0?'+':'') + p.toFixed(1) + '%';
const esc = s => String(s||'').replace(/&/g,'&amp;').replace(/</g,'&lt;').replace(/>/g,'&gt;').replace(/"/g,'&quot;');

// Tabs
document.querySelectorAll('nav button').forEach(btn => {
  btn.addEventListener('click', () => {
    document.querySelectorAll('nav button').forEach(b => b.classList.remove('on'));
    document.querySelectorAll('section').forEach(s => s.classList.remove('on'));
    btn.classList.add('on');
    document.getElementById(btn.dataset.tab).classList.add('on');
    if (btn.dataset.tab === 'sosanh') fillCmp();
  });
});

// Render Tổng Sản Lượng
(()=>{
  const max = Math.max(...TONG);
  document.getElementById('chartTong').innerHTML = MONTHS.map((m, i) => `
    <div class="bar-row">
      <div class="lbl">${m} (${DAYS[i]}N)</div>
      <div class="track"><div class="fill" style="width:${(TONG[i]/max*100).toFixed(1)}%">${num(TONG[i])} Kg</div></div>
      <div class="val">${num(TONG[i])}</div>
    </div>`).join('');
})();

// Render TB/ngày
(()=>{
  const max = Math.max(...TBARR);
  document.getElementById('chartTB').innerHTML = MONTHS.map((m, i) => `
    <div class="bar-row">
      <div class="lbl">${m}</div>
      <div class="track"><div class="fill" style="width:${(TBARR[i]/max*100).toFixed(1)}%">${num(TBARR[i])} Kg/N</div></div>
      <div class="val">${num(TBARR[i])}</div>
    </div>`).join('');
})();

// Top 15 KH
(()=>{
  const top15 = [...KH].sort((a,b) => b.tb[b.tb.length-1] - a.tb[a.tb.length-1]).slice(0, 15);
  const max = top15[0].tb[top15[0].tb.length-1] || 1;
  document.getElementById('chartTop').innerHTML = top15.map(k => {
    const val = k.tb[k.tb.length-1];
    const cls = k.chenh > 0 ? 'green' : (k.chenh < 0 ? 'red' : '');
    return `<div class="bar-row">
      <div class="lbl" title="${esc(k.ten)}">${esc(k.ten)}</div>
      <div class="track"><div class="fill ${cls}" style="width:${(val/max*100).toFixed(1)}%">${num(val)}</div></div>
      <div class="val">${num(val)}</div>
    </div>`;
  }).join('');
})();

// Table chi tiết
let sortKey = 'stt', sortAsc = true;
function diffHtml(d, pct){
  if (d > 0) return `<span class="pill duong">+${num(d)} (+${pct.toFixed(1)}%)</span>`;
  if (d < 0) return `<span class="pill do">${num(d)} (${pct.toFixed(1)}%)</span>`;
  return `<span class="pill xam">0 (0.0%)</span>`;
}

function renderTable(){
  const q = document.getElementById('khSearch').value.toLowerCase().trim();
  const tr = document.getElementById('khTrend').value;
  const min = Number(document.getElementById('khMin').value) || 0;

  let list = KH.filter(k => {
    const lastTb = k.tb[k.tb.length-1];
    if (min > 0 && lastTb < min) return false;
    if (tr === 'up' && k.chenh <= 0) return false;
    if (tr === 'down' && k.chenh >= 0) return false;
    if (tr === 'flat' && k.chenh !== 0) return false;
    if (q && !k.ma.toLowerCase().includes(q) && !k.ten.toLowerCase().includes(q) && !(k.nm||'').toLowerCase().includes(q)) return false;
    return true;
  });

  list.sort((a, b) => {
    let va = a[sortKey], vb = b[sortKey];
    if (sortKey.startsWith('t') && sortKey.length <= 3) {
      const idx = Number(sortKey.slice(1));
      va = a.tb[idx] || 0; vb = b.tb[idx] || 0;
    }
    if (typeof va === 'string') return sortAsc ? va.localeCompare(vb, 'vi') : vb.localeCompare(va, 'vi');
    return sortAsc ? (va - vb) : (vb - va);
  });

  const tbody = document.querySelector('#khTable tbody');
  tbody.innerHTML = list.map(k => `
    <tr>
      <td>${k.stt}</td><td><b>${esc(k.ma)}</b></td><td title="${esc(k.ten)}">${esc(k.ten)}</td>
      <td>${k.nm ? esc(k.nm) : "—"}</td>
      ${k.tb.map(v => `<td class="num">${v ? num(v) : '-'}</td>`).join('')}
      <td class="num ${k.chenh>0?'diff-up':(k.chenh<0?'diff-down':'diff-zero')}">${k.chenh>0?'+':''}${num(k.chenh)}</td>
      <td class="num">${diffHtml(k.chenh, k.pct)}</td>
    </tr>`).join('');

  document.getElementById('khCount').textContent = `Hiển thị ${list.length} / ${KH.length} khách hàng`;
}

document.querySelectorAll('#khTable thead th').forEach(th => {
  th.addEventListener('click', () => {
    const k = th.dataset.k;
    if (sortKey === k) sortAsc = !sortAsc;
    else { sortKey = k; sortAsc = (k === 'ten' || k === 'ma' || k === 'stt'); }
    document.querySelectorAll('#khTable thead th').forEach(h => h.classList.remove('asc','desc'));
    th.classList.add(sortAsc ? 'asc' : 'desc');
    renderTable();
  });
});

['khSearch','khTrend','khMin'].forEach(id => {
  document.getElementById(id).addEventListener('input', renderTable);
});
document.getElementById('khReset').addEventListener('click', () => {
  document.getElementById('khSearch').value = '';
  document.getElementById('khTrend').value = '';
  document.getElementById('khMin').value = '0';
  renderTable();
});
renderTable();

// Top Tăng / Giảm
(()=>{
  const up = [...KH].filter(k => k.chenh > 0).sort((a, b) => b.chenh - a.chenh).slice(0, 10);
  const down = [...KH].filter(k => k.chenh < 0).sort((a, b) => a.chenh - b.chenh).slice(0, 10);
  const maxU = Math.max(...up.map(k => k.chenh), 1);
  const maxD = Math.max(...down.map(k => -k.chenh), 1);

  document.getElementById('topUp').innerHTML = up.map(k => `
    <div class="bar-row"><div class="lbl" title="${esc(k.ten)}">${esc(k.ten)}</div>
    <div class="track"><div class="fill green" style="width:${(k.chenh/maxU*100).toFixed(1)}%">+${num(k.chenh)}</div></div>
    <div class="val">${fmtPct(k.pct)}</div></div>`).join('');

  document.getElementById('topDown').innerHTML = down.map(k => `
    <div class="bar-row"><div class="lbl" title="${esc(k.ten)}">${esc(k.ten)}</div>
    <div class="track"><div class="fill red" style="width:${(-k.chenh/maxD*100).toFixed(1)}%">${num(k.chenh)}</div></div>
    <div class="val">${fmtPct(k.pct)}</div></div>`).join('');
})();

// So sánh
function fillCmp(){
  const opts = [...KH].sort((a, b) => a.ten.localeCompare(b.ten, 'vi')).map(k => `<option value="${k.stt}">${esc(k.ten)} (${esc(k.ma)})${k.nm ? " · NM " + esc(k.nm) : ""}</option>`).join('');
  ['cmpA','cmpB'].forEach(id => {
    const sel = document.getElementById(id);
    if (sel.options.length < 2) sel.innerHTML = opts;
  });
}

document.getElementById('cmpGo').addEventListener('click', () => {
  const a = KH.find(k => k.stt == Number(document.getElementById('cmpA').value));
  const b = KH.find(k => k.stt == Number(document.getElementById('cmpB').value));
  if (!a || !b) {
    document.getElementById('cmpResult').innerHTML = '<p class="hint">⚠️ Vui lòng chọn đủ 2 khách hàng.</p>';
    document.getElementById('cmpResult').style.display = 'block';
    return;
  }
  const max = Math.max(...a.tb, ...b.tb, 1);
  const card = k => `
    <div style="flex:1;min-width:300px;background:#f8fafc;border-radius:10px;padding:14px;border:1px solid #e3e8ef">
      <h4 style="color:var(--xanh);margin-bottom:8px;font-size:13.5px">${esc(k.ten)} <span style="color:#8a94a6;font-weight:400">(${esc(k.ma)})</span></h4>
      ${k.nm ? `<p style="font-size:12px;color:#8a94a6;margin:-4px 0 8px">Nhà máy: <b style="color:#2E5E9E">${esc(k.nm)}</b></p>` : ""}
      ${MONTHS.map((m, i) => `
        <div class="bar-row" style="margin:3px 0"><div class="lbl" style="width:74px;font-size:11px">${m}</div>
        <div class="track" style="height:16px"><div class="fill" style="width:${(k.tb[i]/max*100).toFixed(1)}%;font-size:10px;min-width:26px">${num(k.tb[i])}</div></div>
        <div class="val" style="width:44px;font-size:11px">${num(k.tb[i])}</div></div>`).join('')}
      <p style="font-size:12px;margin-top:8px">TB/ngày Kỳ T9: <b style="color:var(--xanh)">${num(k.tb[k.tb.length-1])}</b> Kg/ngày — ${diffHtml(k.chenh, k.pct)}</p>
    </div>`;
  document.getElementById('cmpResult').innerHTML = `<div style="display:flex;gap:14px;flex-wrap:wrap">${card(a)}${card(b)}</div>`;
  document.getElementById('cmpResult').style.display = 'block';
});
</script>
</body>
</html>
'''


if __name__ == "__main__":
    ap = argparse.ArgumentParser()
    ap.add_argument("src")
    ap.add_argument("--out", default=None)
    a = ap.parse_args()
    out = a.out or os.path.join(os.path.dirname(os.path.abspath(a.src)),
                                "Bao_cao_MuaHang_portal.html")
    r = build(a.src, out)
    print(f"KH: {r['kh']} | gắn nhà máy: {r['nha_may']} | {r['ky']}")
    print(f"Tổng {r['tong']:,.0f} Kg | TB {r['tb']:,.0f} Kg/ngày | chênh {r['ch']:+,.0f} ({r['pct']:+.1f}%)")
    print("SAVED:", r["out"], f"({r['size']:,} chars)")
