// Shared data, icons and helpers for the Finanzas prototype.
// All exports go on window so sibling Babel scripts can read them.

const FinanzasIcon = ({ name, size = 20, stroke = 1.75, style }) => {
  const p = {
    home:        <><path d="M3 9.5 12 3l9 6.5V20a1 1 0 0 1-1 1h-5v-7h-6v7H4a1 1 0 0 1-1-1V9.5Z"/></>,
    list:        <><line x1="8" y1="6" x2="21" y2="6"/><line x1="8" y1="12" x2="21" y2="12"/><line x1="8" y1="18" x2="21" y2="18"/><circle cx="4" cy="6" r="1"/><circle cx="4" cy="12" r="1"/><circle cx="4" cy="18" r="1"/></>,
    budget:      <><path d="M21 12a9 9 0 1 1-9-9"/><path d="M21 12A9 9 0 0 0 12 3v9h9Z"/></>,
    wallet:      <><path d="M3 7a2 2 0 0 1 2-2h13v4"/><path d="M3 7v11a2 2 0 0 0 2 2h15a1 1 0 0 0 1-1v-3"/><path d="M21 11h-4a2.5 2.5 0 0 0 0 5h4v-5Z"/></>,
    chart:       <><path d="M3 3v18h18"/><path d="M7 14l4-4 4 4 5-6"/></>,
    settings:    <><circle cx="12" cy="12" r="3"/><path d="M19.4 15a1.65 1.65 0 0 0 .33 1.82l.06.06a2 2 0 0 1-2.83 2.83l-.06-.06a1.65 1.65 0 0 0-1.82-.33 1.65 1.65 0 0 0-1 1.51V21a2 2 0 0 1-4 0v-.09A1.65 1.65 0 0 0 9 19.4a1.65 1.65 0 0 0-1.82.33l-.06.06a2 2 0 0 1-2.83-2.83l.06-.06A1.65 1.65 0 0 0 4.6 15a1.65 1.65 0 0 0-1.51-1H3a2 2 0 0 1 0-4h.09A1.65 1.65 0 0 0 4.6 9 1.65 1.65 0 0 0 4.27 7.18l-.06-.06a2 2 0 0 1 2.83-2.83l.06.06A1.65 1.65 0 0 0 9 4.6a1.65 1.65 0 0 0 1-1.51V3a2 2 0 0 1 4 0v.09a1.65 1.65 0 0 0 1 1.51 1.65 1.65 0 0 0 1.82-.33l.06-.06a2 2 0 0 1 2.83 2.83l-.06.06A1.65 1.65 0 0 0 19.4 9c.13.31.21.65.21 1H21a2 2 0 0 1 0 4h-.09a1.65 1.65 0 0 0-1.51 1Z"/></>,
    plus:        <><line x1="12" y1="5" x2="12" y2="19"/><line x1="5" y1="12" x2="19" y2="12"/></>,
    minus:       <line x1="5" y1="12" x2="19" y2="12"/>,
    x:           <><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></>,
    chevR:       <polyline points="9 6 15 12 9 18"/>,
    chevL:       <polyline points="15 18 9 12 15 6"/>,
    chevDown:    <polyline points="6 9 12 15 18 9"/>,
    arrowUp:     <><line x1="12" y1="19" x2="12" y2="5"/><polyline points="5 12 12 5 19 12"/></>,
    arrowDown:   <><line x1="12" y1="5" x2="12" y2="19"/><polyline points="19 12 12 19 5 12"/></>,
    search:      <><circle cx="11" cy="11" r="8"/><path d="m21 21-4.3-4.3"/></>,
    filter:      <><path d="M3 6h18"/><path d="M7 12h10"/><path d="M10 18h4"/></>,
    bell:        <><path d="M18 8A6 6 0 0 0 6 8c0 7-3 9-3 9h18s-3-2-3-9"/><path d="M13.7 21a2 2 0 0 1-3.4 0"/></>,
    calendar:    <><rect x="3" y="4" width="18" height="18" rx="2"/><line x1="16" y1="2" x2="16" y2="6"/><line x1="8" y1="2" x2="8" y2="6"/><line x1="3" y1="10" x2="21" y2="10"/></>,
    tag:         <><path d="M20.59 13.41 13.41 20.59a2 2 0 0 1-2.82 0L2 12V2h10l8.59 8.59a2 2 0 0 1 0 2.82Z"/><line x1="7" y1="7" x2="7.01" y2="7"/></>,
    eye:         <><path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/></>,
    eyeOff:      <><path d="M17.94 17.94A10.07 10.07 0 0 1 12 20c-7 0-11-8-11-8a18.45 18.45 0 0 1 5.06-5.94M9.9 4.24A9.12 9.12 0 0 1 12 4c7 0 11 8 11 8a18.5 18.5 0 0 1-2.16 3.19m-6.72-1.07a3 3 0 1 1-4.24-4.24"/><line x1="1" y1="1" x2="23" y2="23"/></>,
    // Categories
    food:        <><path d="M3 11h18l-1.5 9.5a1.5 1.5 0 0 1-1.5 1.5H6a1.5 1.5 0 0 1-1.5-1.5L3 11Z"/><path d="M7 11V8a5 5 0 0 1 10 0v3"/><path d="M12 2v3"/></>,
    car:         <><path d="M5 17h14M3 10l2-5h14l2 5M5 10h14v7H5z"/><circle cx="7.5" cy="17.5" r="1.5"/><circle cx="16.5" cy="17.5" r="1.5"/></>,
    home2:       <><path d="M3 9.5 12 3l9 6.5V21H3V9.5Z"/><path d="M9 21v-7h6v7"/></>,
    shop:        <><path d="M6 7h12l-1 13H7L6 7Z"/><path d="M9 7V5a3 3 0 0 1 6 0v2"/></>,
    sub:         <><rect x="3" y="5" width="18" height="14" rx="2"/><path d="M3 10h18"/><path d="M7 15h3"/></>,
    health:      <><path d="M12 21s-7-4.5-7-10a4.5 4.5 0 0 1 7-3.5A4.5 4.5 0 0 1 19 11c0 5.5-7 10-7 10Z"/></>,
    fun:         <><circle cx="12" cy="12" r="9"/><path d="M8 14s1.5 2 4 2 4-2 4-2"/><line x1="9" y1="9" x2="9.01" y2="9"/><line x1="15" y1="9" x2="15.01" y2="9"/></>,
    travel:      <><path d="M17.8 19.2 16 11l3.5-3.5C21 6 21.5 4 21 3c-1-.5-3 0-4.5 1.5L13 8 4.8 6.2c-.5-.1-.9.1-1.1.5L3 7.5c-.2.4-.1.9.3 1.1L9 12l-3 3-2-.5c-.4 0-.7.2-.9.5L3 15.5c-.2.4-.1.8.3 1L8 19l2.5 4.4c.2.4.6.5 1 .3l.5-.2c.3-.2.5-.5.5-.9L12 20l3-3 3.6 5.7c.2.4.7.5 1.1.3l.4-.3c.4-.2.6-.6.5-1.1Z"/></>,
    money:       <><line x1="12" y1="1" x2="12" y2="23"/><path d="M17 5H9.5a3.5 3.5 0 0 0 0 7h5a3.5 3.5 0 0 1 0 7H6"/></>,
    coffee:      <><path d="M17 8h1a4 4 0 1 1 0 8h-1"/><path d="M3 8h14v9a4 4 0 0 1-4 4H7a4 4 0 0 1-4-4V8Z"/><line x1="6" y1="2" x2="6" y2="5"/><line x1="10" y1="2" x2="10" y2="5"/><line x1="14" y1="2" x2="14" y2="5"/></>,
    receipt:     <><path d="M4 2v20l2-2 2 2 2-2 2 2 2-2 2 2 2-2 2 2V2l-2 2-2-2-2 2-2-2-2 2-2-2-2 2-2-2Z"/><line x1="8" y1="8" x2="16" y2="8"/><line x1="8" y1="12" x2="16" y2="12"/><line x1="8" y1="16" x2="13" y2="16"/></>,
    bank:        <><path d="M2 10h20L12 3 2 10Z"/><path d="M4 10v9M9 10v9M15 10v9M20 10v9"/><path d="M2 22h20"/></>,
    card:        <><rect x="2" y="6" width="20" height="14" rx="2"/><line x1="2" y1="11" x2="22" y2="11"/></>,
    piggy:       <><path d="M19 11.5a5.5 5.5 0 0 0-.7-2.7l1.7-1.5-1.6-1.4-2 1.2A8 8 0 0 0 12 6c-4.4 0-8 3.4-8 7.5 0 1.6.5 3 1.5 4.2L4 19v2h3l1.4-1.4A8.5 8.5 0 0 0 12 21c3.5 0 6.5-2 7.6-4.8H22v-3h-3.1c.1-.5.1-1 .1-1.7Z"/><circle cx="15" cy="11" r="1"/></>,
  };
  return (
    <svg viewBox="0 0 24 24" width={size} height={size} fill="none"
      stroke="currentColor" strokeWidth={stroke}
      strokeLinecap="round" strokeLinejoin="round" style={{ flexShrink: 0, ...style }}>
      {p[name] || null}
    </svg>
  );
};

// ─────────────────────────────────────────────────────────────
// Currency formatter (MXN)
// ─────────────────────────────────────────────────────────────
const fmtMXN = (n, { sign = false, hide = false } = {}) => {
  if (hide) return "$ • • • • •";
  const abs = Math.abs(n);
  const s = abs.toLocaleString("es-MX", { minimumFractionDigits: 2, maximumFractionDigits: 2 });
  const prefix = sign ? (n < 0 ? "−" : "+") : (n < 0 ? "−" : "");
  return `${prefix}$${s}`;
};

const fmtCompact = (n) => {
  const abs = Math.abs(n);
  if (abs >= 1000) return `$${(abs / 1000).toFixed(1).replace(/\.0$/, "")}k`;
  return `$${abs.toFixed(0)}`;
};

// ─────────────────────────────────────────────────────────────
// Demo data — seeded for the May 2026 month
// ─────────────────────────────────────────────────────────────
const FINANZAS_CATEGORIES = [
  { id: "comida",     label: "Comida",        icon: "food",    color: "#c0392b" },
  { id: "transporte", label: "Transporte",    icon: "car",     color: "#1a2a5e" },
  { id: "casa",       label: "Casa",          icon: "home2",   color: "#2f4a92" },
  { id: "compras",    label: "Compras",       icon: "shop",    color: "#c98415" },
  { id: "suscrip",    label: "Suscripciones", icon: "sub",     color: "#4a66b0" },
  { id: "salud",      label: "Salud",         icon: "health",  color: "#2a8a5f" },
  { id: "ocio",       label: "Ocio",          icon: "fun",     color: "#6a8fd6" },
  { id: "viaje",      label: "Viajes",        icon: "travel",  color: "#243a78" },
  { id: "cafe",       label: "Café",          icon: "coffee",  color: "#8b5a2b" },
  { id: "ingreso",    label: "Ingreso",       icon: "money",   color: "#2a8a5f" },
  { id: "transfer",   label: "Transferencia", icon: "wallet",  color: "#5a6486" },
];

// Real data lives in Supabase (loaded into storage cache). These empty arrays
// are kept only as last-resort fallbacks if storage isn't initialized.
const FINANZAS_ACCOUNTS = [];
const FINANZAS_TX = [];
const FINANZAS_BUDGETS = [];

// helpers
const catBy = (id) => FINANZAS_CATEGORIES.find(c => c.id === id);
const accBy = (id) => {
  const live = window.finanzasStorage ? window.finanzasStorage.loadAccounts() : FINANZAS_ACCOUNTS;
  return live.find(a => a.id === id)
      || { id, name: "Cuenta", type: "", balance: 0, color: "#5a6486", last4: null };
};

const totalBalance = (accs) => accs.reduce((s, a) => s + a.balance, 0);
const monthSpending = (txs) => txs.filter(t => t.amount < 0 && t.cat !== "transfer").reduce((s, t) => s + Math.abs(t.amount), 0);
const monthIncome   = (txs) => txs.filter(t => t.amount > 0 && t.cat !== "transfer").reduce((s, t) => s + t.amount, 0);

// Group total spend by category
const spendByCategory = (txs) => {
  const map = {};
  for (const t of txs) {
    if (t.amount >= 0) continue;
    if (t.cat === "transfer") continue;
    map[t.cat] = (map[t.cat] || 0) + Math.abs(t.amount);
  }
  return Object.entries(map)
    .map(([id, total]) => ({ ...catBy(id), total }))
    .sort((a, b) => b.total - a.total);
};

// Smart category suggestion based on description keywords
const suggestCategory = (desc) => {
  const s = (desc || "").toLowerCase();
  const rules = [
    [/starbucks|cafe|café|coffee|cardinal/, "cafe"],
    [/uber|didi|taxi|metro|cabify|gasolina/, "transporte"],
    [/pujol|tacos|restaurant|walmart|chedraui|super|comida|cena/, "comida"],
    [/spotify|netflix|icloud|apple|disney|hbo|prime/, "suscrip"],
    [/cfe|agua|gas|telmex|izzi|totalplay|renta/, "casa"],
    [/farmacia|hospital|doctor|salud/, "salud"],
    [/cinepolis|cinema|spotify|concierto/, "ocio"],
    [/liverpool|amazon|mercadolibre|zara|nike/, "compras"],
    [/aeromexico|volaris|hotel|airbnb/, "viaje"],
    [/nomina|nómina|salary|freelance|cliente/, "ingreso"],
  ];
  for (const [re, cat] of rules) if (re.test(s)) return cat;
  return null;
};

// Relative time formatter
const relTime = (iso) => {
  const d = new Date(iso);
  const now = new Date();
  const diff = (now - d) / 1000 / 60;
  if (diff < 1) return "Hace un momento";
  if (diff < 60) return `Hace ${Math.round(diff)} min`;
  if (diff < 60 * 24) return `Hace ${Math.round(diff / 60)} h`;
  const days = Math.round(diff / 60 / 24);
  if (days === 1) return "Ayer";
  if (days < 7) return `Hace ${days} días`;
  return d.toLocaleDateString("es-MX", { day: "numeric", month: "short" });
};

const dayLabel = (iso) => {
  const d = new Date(iso);
  const now = new Date();
  const d0 = new Date(d.getFullYear(), d.getMonth(), d.getDate());
  const n0 = new Date(now.getFullYear(), now.getMonth(), now.getDate());
  const days = Math.floor((n0 - d0) / (1000 * 60 * 60 * 24));
  if (days === 0) return "Hoy";
  if (days === 1) return "Ayer";
  return d.toLocaleDateString("es-MX", { weekday: "long", day: "numeric", month: "long" });
};

// Current month start (1st of this month, 00:00)
const monthStart = () => {
  const n = new Date();
  return new Date(n.getFullYear(), n.getMonth(), 1);
};

// ─────────────────────────────────────────────────────────────
// CSV export
// ─────────────────────────────────────────────────────────────
const csvEscape = (v) => {
  const s = v == null ? "" : String(v);
  return /[",\n;]/.test(s) ? `"${s.replace(/"/g, '""')}"` : s;
};

const exportTxCsv = (txs) => {
  const headers = ["id", "fecha", "monto", "tipo", "categoria", "cuenta", "descripcion", "etiquetas"];
  const lines = [headers.join(",")];
  for (const t of txs) {
    const cat = catBy(t.cat)?.label || t.cat;
    const acc = accBy(t.acc)?.name || t.acc;
    const tipo = t.cat === "transfer" ? "transferencia" : t.amount > 0 ? "ingreso" : "gasto";
    lines.push([
      t.id, t.date, t.amount.toFixed(2), tipo, cat, acc, t.desc,
      (t.tags || []).join("|"),
    ].map(csvEscape).join(","));
  }
  return lines.join("\n");
};

const downloadFile = (filename, contents, mime = "text/csv;charset=utf-8") => {
  const blob = new Blob(["﻿" + contents], { type: mime });
  const url = URL.createObjectURL(blob);
  const a = document.createElement("a");
  a.href = url; a.download = filename;
  document.body.appendChild(a); a.click();
  setTimeout(() => { document.body.removeChild(a); URL.revokeObjectURL(url); }, 100);
};

Object.assign(window, {
  FinanzasIcon,
  fmtMXN, fmtCompact,
  FINANZAS_CATEGORIES, FINANZAS_ACCOUNTS, FINANZAS_TX, FINANZAS_BUDGETS,
  catBy, accBy,
  totalBalance, monthSpending, monthIncome, spendByCategory, suggestCategory,
  relTime, dayLabel, monthStart,
  exportTxCsv, downloadFile,
});
