"use client";

import { createClient } from "@/lib/supabase/client";
import { useWorkspaceStore } from "@/stores/workspace-store";
import { useState, useCallback, useId } from "react";
import {
  Plus,
  Trash2,
  Edit3,
  TrendingUp,
  TrendingDown,
  Camera,
  Check,
  X,
  Upload,
  FolderOpen,
} from "lucide-react";

/* ─── Types ─── */

interface NetWorthEntry {
  id: string;
  category:
    | "cash"
    | "investments"
    | "business"
    | "property"
    | "crypto"
    | "vehicle"
    | "other_asset";
  label: string;
  amount: number; // in cents
  updatedAt: string;
  details?: {
    source?: "manual" | "business_valuation" | "property_calculation";
    ownershipPercent?: number | null;
    valuationMethod?: "revenue" | "profit" | null;
    baseAnnualCents?: number | null;
    multiple?: number | null;
    marketValueCents?: number | null;
    mortgageCents?: number | null;
    vaultNoteId?: string | null;
  } | null;
}

interface NetWorthLiability {
  id: string;
  category:
    | "mortgage"
    | "car_loan"
    | "credit_card"
    | "student_loan"
    | "other_debt";
  label: string;
  amount: number; // in cents
  updatedAt: string;
  details?: {
    source?: "manual" | "property_calculation";
    ownershipPercent?: number | null;
    linkedAssetId?: string | null;
    vaultNoteId?: string | null;
  } | null;
}

interface MonthlySnapshot {
  month: string; // "2025-04"
  assets: number;
  liabilities: number;
  netWorth: number;
}

/* ─── Constants ─── */

const ASSET_CATEGORIES: {
  value: NetWorthEntry["category"];
  label: string;
  icon: string;
}[] = [
  { value: "cash", label: "Bargeld", icon: "💰" },
  { value: "investments", label: "Investments", icon: "📈" },
  { value: "business", label: "Firma", icon: "🏢" },
  { value: "property", label: "Immobilien", icon: "🏠" },
  { value: "crypto", label: "Krypto", icon: "₿" },
  { value: "vehicle", label: "Fahrzeuge", icon: "🚗" },
  { value: "other_asset", label: "Sonstiges", icon: "💎" },
];

const LIABILITY_CATEGORIES: {
  value: NetWorthLiability["category"];
  label: string;
  icon: string;
}[] = [
  { value: "mortgage", label: "Hypothek", icon: "🏦" },
  { value: "car_loan", label: "Autokredit", icon: "🚘" },
  { value: "credit_card", label: "Kreditkarte", icon: "💳" },
  { value: "student_loan", label: "Studienkredit", icon: "🎓" },
  { value: "other_debt", label: "Sonstige Schulden", icon: "📋" },
];

/* ─── Helpers ─── */

function formatEur(cents: number): string {
  return new Intl.NumberFormat("de-DE", {
    style: "currency",
    currency: "EUR",
  }).format(cents / 100);
}

function formatEurCompact(cents: number): string {
  const value = cents / 100;
  if (Math.abs(value) >= 1_000_000) {
    return (
      new Intl.NumberFormat("de-DE", {
        minimumFractionDigits: 1,
        maximumFractionDigits: 1,
      }).format(value / 1_000_000) + " Mio. €"
    );
  }
  if (Math.abs(value) >= 1_000) {
    return (
      new Intl.NumberFormat("de-DE", {
        minimumFractionDigits: 1,
        maximumFractionDigits: 1,
      }).format(value / 1_000) + " Tsd. €"
    );
  }
  return formatEur(cents);
}

function getAssetIcon(category: NetWorthEntry["category"]): string {
  return ASSET_CATEGORIES.find((c) => c.value === category)?.icon ?? "💎";
}

function getLiabilityIcon(category: NetWorthLiability["category"]): string {
  return LIABILITY_CATEGORIES.find((c) => c.value === category)?.icon ?? "📋";
}

function now(): string {
  return new Date().toISOString();
}

function currentMonth(): string {
  const d = new Date();
  return `${d.getFullYear()}-${String(d.getMonth() + 1).padStart(2, "0")}`;
}

function parseEuroInput(value: string): number | null {
  const parsed = parseFloat(value.replace(",", "."));
  if (Number.isNaN(parsed)) return null;
  return Math.round(parsed * 100);
}

function loadStoredState<T>(key: string, fallback: T): T {
  if (typeof window === "undefined") return fallback;

  try {
    const raw = localStorage.getItem(key);
    return raw ? (JSON.parse(raw) as T) : fallback;
  } catch {
    return fallback;
  }
}

function normalizeAsset(entry: NetWorthEntry): NetWorthEntry {
  return {
    ...entry,
    details: entry.details ?? null,
  };
}

function normalizeLiability(entry: NetWorthLiability): NetWorthLiability {
  return {
    ...entry,
    details: entry.details ?? null,
  };
}

function monthLabel(m: string): string {
  const [year, month] = m.split("-");
  return new Date(Number(year), Number(month) - 1, 1).toLocaleDateString(
    "de-DE",
    { month: "short", year: "2-digit" }
  );
}

function buildEntrySummary(entry: NetWorthEntry | NetWorthLiability): string | null {
  if (!entry.details) return null;

  if ("valuationMethod" in entry.details && entry.details.source === "business_valuation") {
    const percent = entry.details.ownershipPercent ?? 100;
    const method = entry.details.valuationMethod === "profit" ? "Gewinn" : "Umsatz";
    const multiple = entry.details.multiple ? ` x${entry.details.multiple.toFixed(1)}` : "";
    return `${percent.toFixed(0)}% Anteil · ${method}${multiple}`;
  }

  if (entry.details.source === "property_calculation") {
    const percent = entry.details.ownershipPercent ?? 100;
    return `${percent.toFixed(0)}% Anteil`;
  }

  return null;
}

/* ─── Inline editable entry row ─── */

interface EntryRowProps {
  label: string;
  icon: string;
  amount: number;
  accent: "emerald" | "rose";
  summary?: string | null;
  busy?: boolean;
  onUpload?: (file: File) => Promise<void> | void;
  vaultHref?: string | null;
  onEdit: (label: string, amount: number) => void;
  onDelete: () => void;
}

function EntryRow({
  label,
  icon,
  amount,
  accent,
  summary,
  busy,
  onUpload,
  vaultHref,
  onEdit,
  onDelete,
}: EntryRowProps) {
  const inputId = useId();
  const [editing, setEditing] = useState(false);
  const [draftLabel, setDraftLabel] = useState(label);
  const [draftAmount, setDraftAmount] = useState(
    String((amount / 100).toFixed(2))
  );
  const [pickerKey, setPickerKey] = useState(0);

  function save() {
    const parsed = parseFloat(draftAmount.replace(",", "."));
    if (!isNaN(parsed) && draftLabel.trim()) {
      onEdit(draftLabel.trim(), Math.round(parsed * 100));
      setEditing(false);
    }
  }

  function cancel() {
    setDraftLabel(label);
    setDraftAmount(String((amount / 100).toFixed(2)));
    setEditing(false);
  }

  const borderColor =
    accent === "emerald"
      ? "border-emerald-500/[0.16]"
      : "border-rose-500/[0.16]";
  const bgColor =
    accent === "emerald" ? "bg-emerald-500/[0.04]" : "bg-rose-500/[0.04]";
  const textAccent =
    accent === "emerald" ? "text-emerald-300" : "text-rose-300";

  if (editing) {
    return (
      <div
        className={`flex items-center gap-2 rounded-xl border ${borderColor} ${bgColor} px-3 py-2`}
      >
        <span className="text-base">{icon}</span>
        <input
          className="min-w-0 flex-1 bg-transparent text-sm text-white outline-none placeholder:text-white/30"
          value={draftLabel}
          onChange={(e) => setDraftLabel(e.target.value)}
          onKeyDown={(e) => e.key === "Enter" && save()}
          autoFocus
        />
        <input
          className="w-28 bg-transparent text-right text-sm text-white outline-none placeholder:text-white/30"
          value={draftAmount}
          onChange={(e) => setDraftAmount(e.target.value)}
          onKeyDown={(e) => e.key === "Enter" && save()}
        />
        <span className="text-xs text-white/40">€</span>
        <button
          onClick={save}
          className="rounded-lg p-1 text-emerald-400 hover:bg-emerald-500/10"
        >
          <Check size={14} />
        </button>
        <button
          onClick={cancel}
          className="rounded-lg p-1 text-white/40 hover:bg-white/[0.06]"
        >
          <X size={14} />
        </button>
      </div>
    );
  }

  return (
    <div
      className={`group flex items-center gap-3 rounded-xl border ${borderColor} ${bgColor} px-3 py-2.5 transition-all`}
    >
      <span className="text-base">{icon}</span>
      <div className="min-w-0 flex-1">
        <p className="truncate text-sm text-white/80">{label}</p>
        {summary && <p className="mt-0.5 truncate text-[11px] text-white/35">{summary}</p>}
      </div>
      <span className={`text-sm font-semibold ${textAccent}`}>
        {formatEur(amount)}
      </span>
      <div className="flex items-center gap-1 opacity-0 transition-opacity group-hover:opacity-100">
        {onUpload && (
          <>
            <input
              key={pickerKey}
              type="file"
              className="hidden"
              id={`${inputId}-${pickerKey}`}
              onChange={async (e) => {
                const file = e.target.files?.[0];
                if (!file) return;
                await onUpload(file);
                setPickerKey((current) => current + 1);
              }}
            />
            <label
              htmlFor={`${inputId}-${pickerKey}`}
              className={`rounded-lg p-1 text-white/40 hover:bg-white/[0.06] hover:text-white/75 ${busy ? "pointer-events-none opacity-40" : "cursor-pointer"}`}
            >
              <Upload size={13} />
            </label>
          </>
        )}
        {vaultHref && (
          <a
            href={vaultHref}
            className="rounded-lg p-1 text-white/40 hover:bg-white/[0.06] hover:text-white/75"
          >
            <FolderOpen size={13} />
          </a>
        )}
        <button
          onClick={() => setEditing(true)}
          className="rounded-lg p-1 text-white/40 hover:bg-white/[0.06] hover:text-white/70"
        >
          <Edit3 size={13} />
        </button>
        <button
          onClick={onDelete}
          className="rounded-lg p-1 text-white/30 hover:bg-rose-500/10 hover:text-rose-400"
        >
          <Trash2 size={13} />
        </button>
      </div>
    </div>
  );
}

/* ─── Add entry form ─── */

interface AddEntryFormProps {
  accent: "emerald" | "rose";
  categories: { value: string; label: string; icon: string }[];
  onAdd: (category: string, label: string, amount: number) => void;
}

function AddEntryForm({ accent, categories, onAdd }: AddEntryFormProps) {
  const [open, setOpen] = useState(false);
  const [category, setCategory] = useState(categories[0].value);
  const [label, setLabel] = useState("");
  const [amount, setAmount] = useState("");

  function submit() {
    const parsed = parseFloat(amount.replace(",", "."));
    if (!isNaN(parsed) && label.trim()) {
      onAdd(category, label.trim(), Math.round(parsed * 100));
      setLabel("");
      setAmount("");
      setCategory(categories[0].value);
      setOpen(false);
    }
  }

  const borderColor =
    accent === "emerald"
      ? "border-emerald-500/[0.18]"
      : "border-rose-500/[0.18]";
  const bgBtn =
    accent === "emerald"
      ? "bg-emerald-500/10 text-emerald-300 hover:bg-emerald-500/20"
      : "bg-rose-500/10 text-rose-300 hover:bg-rose-500/20";
  const bgForm =
    accent === "emerald" ? "bg-emerald-500/[0.04]" : "bg-rose-500/[0.04]";

  if (!open) {
    return (
      <button
        onClick={() => setOpen(true)}
        className={`mt-1 flex w-full items-center justify-center gap-1.5 rounded-xl border border-dashed ${borderColor} py-2.5 text-xs font-medium ${accent === "emerald" ? "text-emerald-400/70 hover:text-emerald-300" : "text-rose-400/70 hover:text-rose-300"} transition-all hover:border-opacity-60`}
      >
        <Plus size={13} />
        Eintrag hinzufügen
      </button>
    );
  }

  return (
    <div
      className={`mt-1 rounded-xl border ${borderColor} ${bgForm} p-3 space-y-2`}
    >
      <select
        value={category}
        onChange={(e) => setCategory(e.target.value)}
        className="w-full rounded-lg border border-white/[0.08] bg-white/[0.04] px-3 py-1.5 text-sm text-white outline-none"
      >
        {categories.map((c) => (
          <option key={c.value} value={c.value} className="bg-[#0a0a0d]">
            {c.icon} {c.label}
          </option>
        ))}
      </select>
      <input
        placeholder="Bezeichnung"
        value={label}
        onChange={(e) => setLabel(e.target.value)}
        onKeyDown={(e) => e.key === "Enter" && submit()}
        className="w-full rounded-lg border border-white/[0.08] bg-white/[0.04] px-3 py-1.5 text-sm text-white outline-none placeholder:text-white/30"
        autoFocus
      />
      <div className="flex items-center gap-2">
        <input
          placeholder="Betrag in €"
          value={amount}
          onChange={(e) => setAmount(e.target.value)}
          onKeyDown={(e) => e.key === "Enter" && submit()}
          className="flex-1 rounded-lg border border-white/[0.08] bg-white/[0.04] px-3 py-1.5 text-sm text-white outline-none placeholder:text-white/30"
        />
        <button
          onClick={submit}
          className={`rounded-lg px-3 py-1.5 text-sm font-medium ${bgBtn} transition-all`}
        >
          <Check size={14} />
        </button>
        <button
          onClick={() => setOpen(false)}
          className="rounded-lg px-3 py-1.5 text-sm text-white/40 hover:bg-white/[0.06]"
        >
          <X size={14} />
        </button>
      </div>
    </div>
  );
}

interface NetWorthCalculatorProps {
  onAddBusiness: (payload: {
    label: string;
    method: "revenue" | "profit";
    baseAnnualCents: number;
    multiple: number;
    ownershipPercent: number;
  }) => void;
  onAddProperty: (payload: {
    label: string;
    propertyValueCents: number;
    mortgageCents: number;
    ownershipPercent: number;
  }) => void;
}

function NetWorthCalculator({ onAddBusiness, onAddProperty }: NetWorthCalculatorProps) {
  const [businessLabel, setBusinessLabel] = useState("");
  const [businessMethod, setBusinessMethod] = useState<"revenue" | "profit">("revenue");
  const [annualRevenue, setAnnualRevenue] = useState("");
  const [monthlyProfit, setMonthlyProfit] = useState("");
  const [multiple, setMultiple] = useState("2.0");
  const [businessOwnershipPercent, setBusinessOwnershipPercent] = useState("100");

  const [propertyLabel, setPropertyLabel] = useState("");
  const [propertyValue, setPropertyValue] = useState("");
  const [mortgageValue, setMortgageValue] = useState("");
  const [ownershipPercent, setOwnershipPercent] = useState("100");

  const businessBaseCents =
    businessMethod === "revenue"
      ? parseEuroInput(annualRevenue)
      : (() => {
          const monthly = parseEuroInput(monthlyProfit);
          return monthly === null ? null : monthly * 12;
        })();
  const multipleValue = Number.parseFloat(multiple.replace(",", "."));
  const businessValuationCents =
    businessBaseCents !== null && !Number.isNaN(multipleValue)
      ? Math.round(businessBaseCents * multipleValue)
      : null;
  const businessOwnershipValue = Number.parseFloat(businessOwnershipPercent.replace(",", "."));
  const normalizedBusinessOwnership =
    Number.isNaN(businessOwnershipValue) ? null : Math.max(0, Math.min(100, businessOwnershipValue));
  const ownedBusinessValueCents =
    businessValuationCents !== null && normalizedBusinessOwnership !== null
      ? Math.round(businessValuationCents * (normalizedBusinessOwnership / 100))
      : null;

  const propertyValueCents = parseEuroInput(propertyValue);
  const mortgageCents = parseEuroInput(mortgageValue) ?? 0;
  const ownershipValue = Number.parseFloat(ownershipPercent.replace(",", "."));
  const normalizedOwnership =
    Number.isNaN(ownershipValue) ? null : Math.max(0, Math.min(100, ownershipValue));
  const propertyEquityCents =
    propertyValueCents !== null && normalizedOwnership !== null
      ? Math.round((propertyValueCents - mortgageCents) * (normalizedOwnership / 100))
      : null;

  function submitBusiness() {
    if (
      !businessLabel.trim() ||
      businessBaseCents === null ||
      Number.isNaN(multipleValue) ||
      normalizedBusinessOwnership === null
    ) return;
    onAddBusiness({
      label: businessLabel.trim(),
      method: businessMethod,
      baseAnnualCents: businessBaseCents,
      multiple: multipleValue,
      ownershipPercent: normalizedBusinessOwnership,
    });
    setBusinessLabel("");
    setAnnualRevenue("");
    setMonthlyProfit("");
    setMultiple("2.0");
    setBusinessOwnershipPercent("100");
  }

  function submitProperty() {
    if (!propertyLabel.trim() || propertyValueCents === null || normalizedOwnership === null) return;
    onAddProperty({
      label: propertyLabel.trim(),
      propertyValueCents,
      mortgageCents,
      ownershipPercent: normalizedOwnership,
    });
    setPropertyLabel("");
    setPropertyValue("");
    setMortgageValue("");
    setOwnershipPercent("100");
  }

  return (
    <div className="grid gap-5 xl:grid-cols-2">
      <div className="rounded-[28px] border border-violet-500/[0.16] bg-[radial-gradient(ellipse_at_top_left,rgba(139,92,246,0.08),rgba(10,8,18,0.98)_55%,rgba(9,8,15,1)_100%)] p-6">
        <div className="mb-5 flex items-center justify-between">
          <div>
            <p className="text-[11px] uppercase tracking-widest text-white/30">Net Worth Rechner</p>
            <h3 className="mt-1 text-lg font-bold text-white">Firma bewerten</h3>
            <p className="mt-1 text-sm text-white/40">Umsatz oder Gewinn mit Multiple bewerten und direkt als Asset übernehmen.</p>
          </div>
          <div className="rounded-2xl border border-violet-500/[0.20] bg-violet-500/10 px-3 py-2 text-right">
            <p className="text-[10px] uppercase tracking-widest text-white/30">Wert</p>
            <p className="text-sm font-bold text-violet-200">
              {ownedBusinessValueCents === null ? "—" : formatEurCompact(ownedBusinessValueCents)}
            </p>
          </div>
        </div>

        <div className="space-y-3">
          <input
            value={businessLabel}
            onChange={(e) => setBusinessLabel(e.target.value)}
            placeholder="Firma / Beteiligung"
            className="w-full rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
          />
          <div className="grid gap-3 md:grid-cols-4">
            <select
              value={businessMethod}
              onChange={(e) => setBusinessMethod(e.target.value as "revenue" | "profit")}
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none"
            >
              <option value="revenue" className="bg-[#0a0a0d]">Umsatz-Multiple</option>
              <option value="profit" className="bg-[#0a0a0d]">Gewinn-Multiple</option>
            </select>
            <input
              value={businessMethod === "revenue" ? annualRevenue : monthlyProfit}
              onChange={(e) => businessMethod === "revenue" ? setAnnualRevenue(e.target.value) : setMonthlyProfit(e.target.value)}
              placeholder={businessMethod === "revenue" ? "Jahresumsatz €" : "Monatsgewinn €"}
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
            />
            <input
              value={multiple}
              onChange={(e) => setMultiple(e.target.value)}
              placeholder="Multiple"
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
            />
            <input
              value={businessOwnershipPercent}
              onChange={(e) => setBusinessOwnershipPercent(e.target.value)}
              placeholder="Ownership %"
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
            />
          </div>
          <div className="flex items-center justify-between rounded-xl border border-white/[0.06] bg-white/[0.03] px-4 py-3">
            <div>
              <p className="text-xs text-white/35">
                {businessMethod === "revenue" ? "Jahresumsatz × Multiple" : "Jahresgewinn × Multiple"}
              </p>
              <p className="mt-1 text-sm text-white/60">
                {businessBaseCents === null
                  ? "Gib erst Werte ein"
                  : `${formatEurCompact(businessBaseCents)} Basis · ${normalizedBusinessOwnership ?? 0}% Anteil`}
              </p>
            </div>
            <button
              onClick={submitBusiness}
              className="rounded-xl border border-violet-500/[0.24] bg-violet-500/12 px-4 py-2 text-sm font-semibold text-violet-200 transition-colors hover:bg-violet-500/20"
            >
              Als Asset übernehmen
            </button>
          </div>
        </div>
      </div>

      <div className="rounded-[28px] border border-amber-500/[0.16] bg-[radial-gradient(ellipse_at_top_left,rgba(245,158,11,0.08),rgba(10,8,18,0.98)_55%,rgba(9,8,15,1)_100%)] p-6">
        <div className="mb-5 flex items-center justify-between">
          <div>
            <p className="text-[11px] uppercase tracking-widest text-white/30">Net Worth Rechner</p>
            <h3 className="mt-1 text-lg font-bold text-white">Immobilie einrechnen</h3>
            <p className="mt-1 text-sm text-white/40">Marktwert, Restschuld und Anteil erfassen. Asset und Schuld werden sauber getrennt angelegt.</p>
          </div>
          <div className="rounded-2xl border border-amber-500/[0.20] bg-amber-500/10 px-3 py-2 text-right">
            <p className="text-[10px] uppercase tracking-widest text-white/30">Eigenkapital</p>
            <p className={`text-sm font-bold ${propertyEquityCents !== null && propertyEquityCents < 0 ? "text-rose-300" : "text-amber-200"}`}>
              {propertyEquityCents === null ? "—" : formatEurCompact(propertyEquityCents)}
            </p>
          </div>
        </div>

        <div className="space-y-3">
          <input
            value={propertyLabel}
            onChange={(e) => setPropertyLabel(e.target.value)}
            placeholder="Immobilie / Objekt"
            className="w-full rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
          />
          <div className="grid gap-3 md:grid-cols-3">
            <input
              value={propertyValue}
              onChange={(e) => setPropertyValue(e.target.value)}
              placeholder="Marktwert €"
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
            />
            <input
              value={mortgageValue}
              onChange={(e) => setMortgageValue(e.target.value)}
              placeholder="Restschuld €"
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
            />
            <input
              value={ownershipPercent}
              onChange={(e) => setOwnershipPercent(e.target.value)}
              placeholder="Anteil %"
              className="rounded-xl border border-white/[0.08] bg-white/[0.04] px-4 py-2.5 text-sm text-white outline-none placeholder:text-white/30"
            />
          </div>
          <div className="flex items-center justify-between rounded-xl border border-white/[0.06] bg-white/[0.03] px-4 py-3">
            <div>
              <p className="text-xs text-white/35">Wert und Finanzierung getrennt</p>
              <p className="mt-1 text-sm text-white/60">
                {propertyValueCents === null
                  ? "Gib erst Werte ein"
                  : `${formatEurCompact(Math.round(propertyValueCents * ((normalizedOwnership ?? 100) / 100)))} Asset · ${formatEurCompact(Math.round(mortgageCents * ((normalizedOwnership ?? 100) / 100)))} Schuld`}
              </p>
            </div>
            <button
              onClick={submitProperty}
              className="rounded-xl border border-amber-500/[0.24] bg-amber-500/12 px-4 py-2 text-sm font-semibold text-amber-200 transition-colors hover:bg-amber-500/20"
            >
              Immobilie übernehmen
            </button>
          </div>
        </div>
      </div>
    </div>
  );
}

/* ─── Main Page ─── */

export default function NetWorthPage() {
  const [assets, setAssets] = useState<NetWorthEntry[]>(() =>
    loadStoredState<NetWorthEntry[]>("mindavio-networth-assets", []).map(normalizeAsset)
  );
  const [liabilities, setLiabilities] = useState<NetWorthLiability[]>(() =>
    loadStoredState<NetWorthLiability[]>("mindavio-networth-liabilities", []).map(normalizeLiability)
  );
  const [snapshots, setSnapshots] = useState<MonthlySnapshot[]>(() =>
    loadStoredState<MonthlySnapshot[]>("mindavio-networth-snapshots", [])
  );
  const [snapshotTaken, setSnapshotTaken] = useState(false);
  const [uploadingId, setUploadingId] = useState<string | null>(null);
  const [uploadFeedback, setUploadFeedback] = useState<string | null>(null);
  const supabase = createClient();
  const activeTeamId = useWorkspaceStore((state) => state.activeTeamId);

  const buildMonthlySnapshots = useCallback(
    (assetEntries: NetWorthEntry[], liabilityEntries: NetWorthLiability[]) => {
      const month = currentMonth();
      const autoSnapshot: MonthlySnapshot = {
        month,
        assets: assetEntries.reduce((sum, entry) => sum + entry.amount, 0),
        liabilities: liabilityEntries.reduce((sum, entry) => sum + entry.amount, 0),
        netWorth:
          assetEntries.reduce((sum, entry) => sum + entry.amount, 0) -
          liabilityEntries.reduce((sum, entry) => sum + entry.amount, 0),
      };

      const filtered = snapshots.filter((snapshot) => snapshot.month !== month);
      const next = [...filtered, autoSnapshot].sort((a, b) => a.month.localeCompare(b.month));
      setSnapshots(next);
      localStorage.setItem("mindavio-networth-snapshots", JSON.stringify(next));
      return next;
    },
    [snapshots],
  );

  const saveAssets = useCallback((updated: NetWorthEntry[], liabilityEntries = liabilities) => {
    setAssets(updated);
    localStorage.setItem("mindavio-networth-assets", JSON.stringify(updated));
    buildMonthlySnapshots(updated, liabilityEntries);
  }, [buildMonthlySnapshots, liabilities]);

  const saveLiabilities = useCallback((updated: NetWorthLiability[], assetEntries = assets) => {
    setLiabilities(updated);
    localStorage.setItem(
      "mindavio-networth-liabilities",
      JSON.stringify(updated)
    );
    buildMonthlySnapshots(assetEntries, updated);
  }, [assets, buildMonthlySnapshots]);

  const saveSnapshots = useCallback((updated: MonthlySnapshot[]) => {
    setSnapshots(updated);
    localStorage.setItem(
      "mindavio-networth-snapshots",
      JSON.stringify(updated)
    );
  }, []);

  /* Derived values */
  const totalAssets = assets.reduce((s, e) => s + e.amount, 0);
  const totalLiabilities = liabilities.reduce((s, e) => s + e.amount, 0);
  const netWorth = totalAssets - totalLiabilities;
  const isPositive = netWorth >= 0;
  const businessAssets = assets.filter((entry) => entry.category === "business");
  const propertyAssets = assets.filter((entry) => entry.category === "property");
  const liquidAssets = assets.filter((entry) => entry.category === "cash" || entry.category === "investments" || entry.category === "crypto");
  const totalBusinessValue = businessAssets.reduce((sum, entry) => sum + entry.amount, 0);
  const totalPropertyValue = propertyAssets.reduce((sum, entry) => sum + entry.amount, 0);
  const totalLiquidValue = liquidAssets.reduce((sum, entry) => sum + entry.amount, 0);

  const lastUpdated =
    [...assets, ...liabilities].reduce((latest, e) => {
      return e.updatedAt > latest ? e.updatedAt : latest;
    }, "") || null;

  /* Asset operations */
  function addAsset(
    category: string,
    label: string,
    amount: number
  ) {
    const entry: NetWorthEntry = {
      id: crypto.randomUUID(),
      category: category as NetWorthEntry["category"],
      label,
      amount,
      updatedAt: now(),
      details: null,
    };
    saveAssets([...assets, entry], liabilities);
  }

  function editAsset(id: string, label: string, amount: number) {
    saveAssets(
      assets.map((a) =>
        a.id === id ? { ...a, label, amount, updatedAt: now() } : a
      )
    );
  }

  function deleteAsset(id: string) {
    saveAssets(assets.filter((a) => a.id !== id));
  }

  /* Liability operations */
  function addLiability(
    category: string,
    label: string,
    amount: number
  ) {
    const entry: NetWorthLiability = {
      id: crypto.randomUUID(),
      category: category as NetWorthLiability["category"],
      label,
      amount,
      updatedAt: now(),
      details: null,
    };
    saveLiabilities([...liabilities, entry], assets);
  }

  function editLiability(id: string, label: string, amount: number) {
    saveLiabilities(
      liabilities.map((l) =>
        l.id === id ? { ...l, label, amount, updatedAt: now() } : l
      )
    );
  }

  function deleteLiability(id: string) {
    saveLiabilities(liabilities.filter((l) => l.id !== id));
  }

  async function ensureVaultNote(input: {
    id: string;
    kind: "asset" | "liability";
    label: string;
    amount: number;
    existingNoteId?: string | null;
  }) {
    if (input.existingNoteId) return input.existingNoteId;

    const {
      data: { user },
    } = await supabase.auth.getUser();

    if (!user) {
      throw new Error("Nicht angemeldet.");
    }

    const { data, error } = await supabase
      .from("notes")
      .insert({
        user_id: user.id,
        team_id: activeTeamId,
        title: `Vault · Net Worth · ${input.label}`,
        content: {
          type: "net-worth-supporting-documents",
          entry_id: input.id,
          entry_kind: input.kind,
          label: input.label,
          amount_cents: input.amount,
        },
      })
      .select("id")
      .single();

    if (error || !data) {
      throw error || new Error("Vault note konnte nicht erstellt werden.");
    }

    return data.id as string;
  }

  async function uploadSupportDocument(
    target: NetWorthEntry | NetWorthLiability,
    kind: "asset" | "liability",
    file: File
  ) {
    setUploadingId(target.id);
    setUploadFeedback(null);

    try {
      const noteId = await ensureVaultNote({
        id: target.id,
        kind,
        label: target.label,
        amount: target.amount,
        existingNoteId: target.details?.vaultNoteId,
      });

      const formData = new FormData();
      formData.append("entityType", "note");
      formData.append("entityId", noteId);
      formData.append("file", file);

      const response = await fetch("/api/attachments", {
        method: "POST",
        body: formData,
      });

      if (!response.ok) {
        const payload = (await response.json().catch(() => null)) as { error?: string } | null;
        throw new Error(payload?.error || "Upload fehlgeschlagen.");
      }

      if (kind === "asset") {
        saveAssets(
          assets.map((entry) =>
            entry.id === target.id
              ? {
                  ...entry,
                  details: {
                    ...entry.details,
                    vaultNoteId: noteId,
                  },
                  updatedAt: now(),
                }
              : entry
          ),
          liabilities
        );
      } else {
        saveLiabilities(
          liabilities.map((entry) =>
            entry.id === target.id
              ? {
                  ...entry,
                  details: {
                    ...entry.details,
                    vaultNoteId: noteId,
                  },
                  updatedAt: now(),
                }
              : entry
          )
        );
      }

      setUploadFeedback("Beleg wurde in den Vault geladen.");
    } catch (error) {
      setUploadFeedback(error instanceof Error ? error.message : "Upload fehlgeschlagen.");
    } finally {
      setUploadingId(null);
    }
  }

  function addBusinessValuation(payload: {
    label: string;
    method: "revenue" | "profit";
    baseAnnualCents: number;
    multiple: number;
    ownershipPercent: number;
  }) {
    const valuationCents = Math.round(
      payload.baseAnnualCents * payload.multiple * (payload.ownershipPercent / 100)
    );
    const descriptor = payload.method === "revenue" ? "Umsatz" : "Gewinn";
    const entry: NetWorthEntry = {
      id: crypto.randomUUID(),
      category: "business",
      label: `${payload.label} · ${descriptor} x${payload.multiple.toFixed(1)}`,
      amount: valuationCents,
      updatedAt: now(),
      details: {
        source: "business_valuation",
        ownershipPercent: payload.ownershipPercent,
        valuationMethod: payload.method,
        baseAnnualCents: payload.baseAnnualCents,
        multiple: payload.multiple,
        vaultNoteId: null,
      },
    };
    saveAssets([...assets, entry], liabilities);
  }

  function addPropertyCalculation(payload: {
    label: string;
    propertyValueCents: number;
    mortgageCents: number;
    ownershipPercent: number;
  }) {
    const share = payload.ownershipPercent / 100;
    const assetAmount = Math.round(payload.propertyValueCents * share);
    const debtAmount = Math.round(payload.mortgageCents * share);

    const assetId = crypto.randomUUID();
    const assetEntry: NetWorthEntry = {
      id: assetId,
      category: "property",
      label: `${payload.label} · Marktwert ${payload.ownershipPercent.toFixed(0)}%`,
      amount: assetAmount,
      updatedAt: now(),
      details: {
        source: "property_calculation",
        ownershipPercent: payload.ownershipPercent,
        marketValueCents: payload.propertyValueCents,
        mortgageCents: payload.mortgageCents,
        vaultNoteId: null,
      },
    };
    const nextAssets = [...assets, assetEntry];

    if (debtAmount > 0) {
      const liabilityEntry: NetWorthLiability = {
        id: crypto.randomUUID(),
        category: "mortgage",
        label: `${payload.label} · Finanzierung ${payload.ownershipPercent.toFixed(0)}%`,
        amount: debtAmount,
        updatedAt: now(),
        details: {
          source: "property_calculation",
          ownershipPercent: payload.ownershipPercent,
          linkedAssetId: assetId,
          vaultNoteId: null,
        },
      };
      saveAssets(nextAssets, [...liabilities, liabilityEntry]);
      saveLiabilities([...liabilities, liabilityEntry], nextAssets);
      return;
    }

    saveAssets(nextAssets, liabilities);
  }

  /* Snapshot */
  function takeSnapshot() {
    const month = currentMonth();
    const snap: MonthlySnapshot = {
      month,
      assets: totalAssets,
      liabilities: totalLiabilities,
      netWorth,
    };
    const filtered = snapshots.filter((s) => s.month !== month);
    saveSnapshots([...filtered, snap].sort((a, b) =>
      a.month.localeCompare(b.month)
    ));
    setSnapshotTaken(true);
    setTimeout(() => setSnapshotTaken(false), 2000);
  }

  /* Chart: last 6 snapshots */
  const currentAutoSnapshot: MonthlySnapshot = {
    month: currentMonth(),
    assets: totalAssets,
    liabilities: totalLiabilities,
    netWorth,
  };
  const effectiveSnapshots = [
    ...snapshots.filter((snapshot) => snapshot.month !== currentAutoSnapshot.month),
    currentAutoSnapshot,
  ].sort((a, b) => a.month.localeCompare(b.month));
  const chartData = effectiveSnapshots.slice(-6);
  const maxAbsValue = Math.max(
    ...chartData.map((s) => Math.max(Math.abs(s.assets), Math.abs(s.liabilities), Math.abs(s.netWorth))),
    1
  );

  /* Net worth ratio for ring */
  const ratio = totalAssets > 0 ? Math.min(1, (totalAssets - totalLiabilities) / totalAssets) : 0;
  const ringPercent = Math.max(0, Math.min(100, ratio * 100));

  return (
    <div className="min-h-screen bg-background px-4 py-8 text-white md:px-8">
      <div className="mx-auto max-w-6xl space-y-6">

        {/* ─── Hero ─── */}
        <div className="rounded-[28px] border border-emerald-500/[0.14] bg-[radial-gradient(ellipse_at_top_left,rgba(16,185,129,0.10),rgba(10,8,18,0.98)_55%,rgba(9,8,15,1)_100%)] p-8">
          <div className="flex flex-col gap-8 lg:flex-row lg:items-center lg:justify-between">

            {/* Left: numbers */}
            <div className="space-y-1">
              <p className="text-xs font-semibold uppercase tracking-widest text-white/30">
                Gesamtvermögen
              </p>
              <p
                className={`text-[52px] font-black leading-none tabular-nums ${
                  isPositive ? "text-emerald-300" : "text-rose-300"
                }`}
              >
                {formatEurCompact(Math.abs(netWorth))}
                {netWorth < 0 && (
                  <span className="ml-1 text-[32px] text-rose-400/70">−</span>
                )}
              </p>
              <div className="flex items-center gap-2 pt-1">
                {isPositive ? (
                  <TrendingUp size={14} className="text-emerald-400" />
                ) : (
                  <TrendingDown size={14} className="text-rose-400" />
                )}
                <span className="text-xs text-white/40">
                  {isPositive ? "Positives Nettovermögen" : "Negatives Nettovermögen"}
                </span>
              </div>

              <div className="flex items-center gap-6 pt-4">
                <div>
                  <p className="text-[11px] uppercase tracking-widest text-white/30">
                    Aktiva
                  </p>
                  <p className="text-lg font-bold text-emerald-300">
                    {formatEurCompact(totalAssets)}
                  </p>
                </div>
                <div className="h-8 w-px bg-white/[0.08]" />
                <div>
                  <p className="text-[11px] uppercase tracking-widest text-white/30">
                    Passiva
                  </p>
                  <p className="text-lg font-bold text-rose-300">
                    {formatEurCompact(totalLiabilities)}
                  </p>
                </div>
                {lastUpdated && (
                  <>
                    <div className="h-8 w-px bg-white/[0.08]" />
                    <div>
                      <p className="text-[11px] uppercase tracking-widest text-white/30">
                        Aktualisiert
                      </p>
                      <p className="text-sm text-white/50">
                        {new Date(lastUpdated).toLocaleDateString("de-DE", {
                          day: "2-digit",
                          month: "2-digit",
                          year: "numeric",
                        })}
                      </p>
                    </div>
                  </>
                )}
              </div>
            </div>

            {/* Right: ring + snapshot button */}
            <div className="flex flex-col items-center gap-5">
              {/* SVG Ring */}
              <div className="relative flex h-32 w-32 items-center justify-center">
                <svg className="absolute inset-0 -rotate-90" viewBox="0 0 100 100">
                  <circle
                    cx="50"
                    cy="50"
                    r="42"
                    fill="none"
                    stroke="rgba(255,255,255,0.05)"
                    strokeWidth="8"
                  />
                  <circle
                    cx="50"
                    cy="50"
                    r="42"
                    fill="none"
                    stroke={isPositive ? "#10b981" : "#f43f5e"}
                    strokeWidth="8"
                    strokeDasharray={`${2 * Math.PI * 42}`}
                    strokeDashoffset={`${2 * Math.PI * 42 * (1 - ringPercent / 100)}`}
                    strokeLinecap="round"
                    className="transition-all duration-700"
                    opacity="0.7"
                  />
                </svg>
                <div className="text-center">
                  <p
                    className={`text-xl font-black ${
                      isPositive ? "text-emerald-300" : "text-rose-300"
                    }`}
                  >
                    {ringPercent.toFixed(0)}%
                  </p>
                  <p className="text-[10px] text-white/30">Eigenkapital</p>
                </div>
              </div>

              <button
                onClick={takeSnapshot}
                className={`flex items-center gap-2 rounded-xl border px-4 py-2.5 text-sm font-medium transition-all ${
                  snapshotTaken
                    ? "border-emerald-500/[0.30] bg-emerald-500/20 text-emerald-300"
                    : "border-white/[0.10] bg-white/[0.04] text-white/70 hover:border-emerald-500/[0.20] hover:bg-emerald-500/10 hover:text-emerald-300"
                }`}
              >
                {snapshotTaken ? (
                  <Check size={14} />
                ) : (
                  <Camera size={14} />
                )}
                {snapshotTaken ? "Snapshot gespeichert!" : "Monatsstand sichern"}
              </button>
            </div>
          </div>
        </div>

        <NetWorthCalculator
          onAddBusiness={addBusinessValuation}
          onAddProperty={addPropertyCalculation}
        />

        {uploadFeedback && (
          <div className="rounded-[22px] border border-violet-500/[0.14] bg-violet-500/[0.06] px-4 py-3 text-sm text-violet-100">
            {uploadFeedback}
          </div>
        )}

        <div className="grid gap-4 md:grid-cols-3">
          <div className="rounded-[24px] border border-white/[0.06] bg-white/[0.025] p-5">
            <p className="text-[11px] uppercase tracking-widest text-white/30">Liquidität & Märkte</p>
            <p className="mt-2 text-2xl font-black text-emerald-200">{formatEurCompact(totalLiquidValue)}</p>
            <p className="mt-1 text-sm text-white/40">Cash, Investments und Krypto</p>
          </div>
          <div className="rounded-[24px] border border-white/[0.06] bg-white/[0.025] p-5">
            <p className="text-[11px] uppercase tracking-widest text-white/30">Firmenwert</p>
            <p className="mt-2 text-2xl font-black text-violet-200">{formatEurCompact(totalBusinessValue)}</p>
            <p className="mt-1 text-sm text-white/40">{businessAssets.length} Firmen- oder Beteiligungswerte</p>
          </div>
          <div className="rounded-[24px] border border-white/[0.06] bg-white/[0.025] p-5">
            <p className="text-[11px] uppercase tracking-widest text-white/30">Immobilien</p>
            <p className="mt-2 text-2xl font-black text-amber-200">{formatEurCompact(totalPropertyValue)}</p>
            <p className="mt-1 text-sm text-white/40">{propertyAssets.length} Immobilienwerte im Bestand</p>
          </div>
        </div>

        {/* ─── Two-column grid ─── */}
        <div className="grid gap-5 lg:grid-cols-2">

          {/* Assets column */}
          <div className="rounded-[28px] border border-emerald-500/[0.16] bg-[radial-gradient(ellipse_at_top_left,rgba(16,185,129,0.08),rgba(10,8,18,0.98)_55%,rgba(9,8,15,1)_100%)] p-6">
            <div className="mb-5 flex items-center justify-between">
              <div className="flex items-center gap-3">
                <div className="flex h-9 w-9 items-center justify-center rounded-xl border border-emerald-500/[0.18] bg-emerald-500/15">
                  <TrendingUp size={16} className="text-emerald-400" />
                </div>
                <div>
                  <h2 className="text-sm font-bold text-white">Aktiva</h2>
                  <p className="text-xs text-white/40">
                    {assets.length} Einträge
                  </p>
                </div>
              </div>
              <span className="text-base font-bold text-emerald-300">
                {formatEur(totalAssets)}
              </span>
            </div>

            <div className="space-y-2">
              {assets.length === 0 && (
                <p className="py-4 text-center text-sm text-white/30">
                  Keine Aktiva eingetragen
                </p>
              )}
              {assets.map((a) => (
                <EntryRow
                  key={a.id}
                  label={a.label}
                  icon={getAssetIcon(a.category)}
                  amount={a.amount}
                  accent="emerald"
                  summary={buildEntrySummary(a)}
                  busy={uploadingId === a.id}
                  onUpload={(file) => uploadSupportDocument(a, "asset", file)}
                  vaultHref={a.details?.vaultNoteId ? `/notes/${a.details.vaultNoteId}` : null}
                  onEdit={(label, amount) => editAsset(a.id, label, amount)}
                  onDelete={() => deleteAsset(a.id)}
                />
              ))}
              <AddEntryForm
                accent="emerald"
                categories={ASSET_CATEGORIES}
                onAdd={addAsset}
              />
            </div>
          </div>

          {/* Liabilities column */}
          <div className="rounded-[28px] border border-rose-500/[0.16] bg-[radial-gradient(ellipse_at_top_left,rgba(244,63,94,0.08),rgba(10,8,18,0.98)_55%,rgba(9,8,15,1)_100%)] p-6">
            <div className="mb-5 flex items-center justify-between">
              <div className="flex items-center gap-3">
                <div className="flex h-9 w-9 items-center justify-center rounded-xl border border-rose-500/[0.18] bg-rose-500/15">
                  <TrendingDown size={16} className="text-rose-400" />
                </div>
                <div>
                  <h2 className="text-sm font-bold text-white">Passiva</h2>
                  <p className="text-xs text-white/40">
                    {liabilities.length} Einträge
                  </p>
                </div>
              </div>
              <span className="text-base font-bold text-rose-300">
                {formatEur(totalLiabilities)}
              </span>
            </div>

            <div className="space-y-2">
              {liabilities.length === 0 && (
                <p className="py-4 text-center text-sm text-white/30">
                  Keine Passiva eingetragen
                </p>
              )}
              {liabilities.map((l) => (
                <EntryRow
                  key={l.id}
                  label={l.label}
                  icon={getLiabilityIcon(l.category)}
                  amount={l.amount}
                  accent="rose"
                  summary={buildEntrySummary(l)}
                  busy={uploadingId === l.id}
                  onUpload={(file) => uploadSupportDocument(l, "liability", file)}
                  vaultHref={l.details?.vaultNoteId ? `/notes/${l.details.vaultNoteId}` : null}
                  onEdit={(label, amount) => editLiability(l.id, label, amount)}
                  onDelete={() => deleteLiability(l.id)}
                />
              ))}
              <AddEntryForm
                accent="rose"
                categories={LIABILITY_CATEGORIES}
                onAdd={addLiability}
              />
            </div>
          </div>
        </div>

        {/* ─── Monthly History ─── */}
        <div className="rounded-[28px] border border-violet-500/[0.14] bg-[radial-gradient(ellipse_at_top_left,rgba(139,92,246,0.08),rgba(10,8,18,0.98)_55%,rgba(9,8,15,1)_100%)] p-6">
          <div className="mb-6 flex items-center justify-between">
            <div className="flex items-center gap-3">
              <div className="flex h-9 w-9 items-center justify-center rounded-xl border border-violet-500/[0.18] bg-violet-500/15">
                <TrendingUp size={16} className="text-violet-400" />
              </div>
              <div>
                <h2 className="text-sm font-bold text-white">
                  Monatsverlauf
                </h2>
                <p className="text-xs text-white/40">
                  Letzte {Math.min(6, chartData.length)} Snapshots
                </p>
              </div>
            </div>
            <div className="flex items-center gap-4 text-xs text-white/40">
              <span className="flex items-center gap-1.5">
                <span className="h-2 w-2 rounded-full bg-emerald-500/70" />
                Aktiva
              </span>
              <span className="flex items-center gap-1.5">
                <span className="h-2 w-2 rounded-full bg-rose-500/70" />
                Passiva
              </span>
              <span className="flex items-center gap-1.5">
                <span className="h-2 w-2 rounded-full bg-violet-500/70" />
                Nettovermögen
              </span>
            </div>
          </div>

          {chartData.length === 0 ? (
            <div className="flex h-40 items-center justify-center">
              <p className="text-sm text-white/30">
                Noch keine Snapshots vorhanden — klicke auf &ldquo;Snapshot aufnehmen&rdquo;
              </p>
            </div>
          ) : (
            <div className="flex h-48 items-end gap-4">
              {chartData.map((snap) => {
                const assetH = Math.round(
                  (Math.abs(snap.assets) / maxAbsValue) * 100
                );
                const liabH = Math.round(
                  (Math.abs(snap.liabilities) / maxAbsValue) * 100
                );
                const nwH = Math.round(
                  (Math.abs(snap.netWorth) / maxAbsValue) * 100
                );
                const nwPos = snap.netWorth >= 0;

                return (
                  <div
                    key={snap.month}
                    className="group flex flex-1 flex-col items-center gap-2"
                  >
                    {/* Bars */}
                    <div className="relative flex w-full items-end justify-center gap-1"
                      style={{ height: "160px" }}>
                      {/* Asset bar */}
                      <div
                        className="w-4 rounded-t-md bg-emerald-500/50 transition-all duration-500 group-hover:bg-emerald-500/80"
                        style={{ height: `${assetH}%` }}
                        title={`Aktiva: ${formatEur(snap.assets)}`}
                      />
                      {/* Liability bar */}
                      <div
                        className="w-4 rounded-t-md bg-rose-500/50 transition-all duration-500 group-hover:bg-rose-500/80"
                        style={{ height: `${liabH}%` }}
                        title={`Passiva: ${formatEur(snap.liabilities)}`}
                      />
                      {/* Net worth bar */}
                      <div
                        className={`w-4 rounded-t-md transition-all duration-500 ${
                          nwPos
                            ? "bg-violet-500/60 group-hover:bg-violet-500/90"
                            : "bg-rose-500/40 group-hover:bg-rose-500/60"
                        }`}
                        style={{ height: `${nwH}%` }}
                        title={`Netto: ${formatEur(snap.netWorth)}`}
                      />
                    </div>

                    {/* Tooltip on hover */}
                    <div className="hidden group-hover:block absolute bottom-12 rounded-lg border border-white/[0.10] bg-[#14121e] px-2.5 py-1.5 text-xs shadow-xl pointer-events-none">
                      <p className="font-semibold text-white/80">{monthLabel(snap.month)}</p>
                      <p className="text-emerald-300">{formatEur(snap.assets)}</p>
                      <p className="text-rose-300">−{formatEur(snap.liabilities)}</p>
                      <p className={nwPos ? "text-violet-300" : "text-rose-300"}>
                        = {formatEur(snap.netWorth)}
                      </p>
                    </div>

                    {/* Month label */}
                    <span className="text-[11px] text-white/40">
                      {monthLabel(snap.month)}
                    </span>
                  </div>
                );
              })}
            </div>
          )}
        </div>
      </div>
    </div>
  );
}
