import type { MerkmalTyp } from "@/lib/merkmale/types";
import { t } from "@/lib/i18n/de";

/**
 * Eine rohe Merkmal-Wert-Zeile aus der DB (siehe `loadMerkmalRows`). Genau eine
 * der drei `value*`-Spalten ist typabhängig gesetzt (oder alle null => leer).
 * `enumLabel` ist das aufgelöste Anzeige-Label aus `merkmal_optionen` (falls
 * vorhanden), `valueText` der gespeicherte enum-Wert.
 */
export interface MerkmalRow {
  merkmalId: string;
  name: string;
  typ: MerkmalTyp;
  einheit: string | null;
  reihenfolge: number;
  valueNum: number | null;
  valueText: string | null;
  valueBool: boolean | null;
  enumLabel: string | null;
}

/** Eine fertig formatierte Eckdaten-Zeile fürs UI. */
export interface Eckdatum {
  merkmalId: string;
  label: string;
  wert: string;
}

/** Schmales geschütztes Leerzeichen (NBSP) zwischen Zahl und Einheit. */
const NBSP = " ";

/**
 * Formatiert eine Zahl im de-AT/de-Stil mit Tausenderpunkt und Dezimalkomma.
 *
 * Bewusst NICHT direkt `Intl.NumberFormat("de-AT")`: je nach ICU-Build liefert
 * de-AT als Gruppentrenner ein schmales geschütztes Leerzeichen (U+202F) statt
 * des fachlich geforderten Tausenderpunkts. Wir normalisieren den Gruppen-
 * trenner deshalb deterministisch auf „.", damit die Ausgabe ICU-unabhängig
 * „14.000" ergibt.
 */
function formatZahl(n: number): string {
  const parts = new Intl.NumberFormat("de-AT").formatToParts(n);
  return parts
    .map((p) => {
      if (p.type === "group") return ".";
      if (p.type === "decimal") return ",";
      return p.value;
    })
    .join("");
}

/**
 * Formatiert EINEN typisierten Merkmalwert als deutschen Anzeige-String.
 *
 * - number: `Intl.NumberFormat("de-AT")` (Tausenderpunkt), Einheit mit NBSP.
 * - boolean: „Ja" / „Nein".
 * - enum: bevorzugt `enumLabel`, sonst der rohe `valueText`.
 * - text: der rohe `valueText`.
 * - leerer/fehlender Wert (für den Typ) => „–".
 *
 * REIN: keine DB-/IO-Abhängigkeit, damit ohne laufendes Postgres testbar.
 */
export function formatMerkmal(row: MerkmalRow): string {
  const leer = t("detail.leerWert");
  switch (row.typ) {
    case "number": {
      if (row.valueNum === null || row.valueNum === undefined) return leer;
      const zahl = formatZahl(row.valueNum);
      return row.einheit ? `${zahl}${NBSP}${row.einheit}` : zahl;
    }
    case "boolean": {
      if (row.valueBool === null || row.valueBool === undefined) return leer;
      return row.valueBool ? t("detail.ja") : t("detail.nein");
    }
    case "enum": {
      const v = row.enumLabel ?? row.valueText;
      return v && v.trim() !== "" ? v : leer;
    }
    case "text": {
      return row.valueText && row.valueText.trim() !== "" ? row.valueText : leer;
    }
    default:
      return leer;
  }
}

/**
 * Wandelt rohe Merkmal-Zeilen in fertige Eckdaten um (sortiert nach
 * `reihenfolge`, dann `name`). Reine Transformation.
 */
export function toEckdaten(rows: MerkmalRow[]): Eckdatum[] {
  return [...rows]
    .sort((a, b) => a.reihenfolge - b.reihenfolge || a.name.localeCompare(b.name, "de"))
    .map((r) => ({
      merkmalId: r.merkmalId,
      label: r.einheit ? `${r.name} (${r.einheit})` : r.name,
      wert: formatMerkmal(r),
    }));
}
