import { Document, Page, Text, View, StyleSheet, renderToBuffer } from "@react-pdf/renderer";
import type { InvoiceDoc } from "@/models/Invoice";
import { formatAddress, formatEUR } from "@/lib/orderConstants";
import { formatNameWithSalutation } from "@/lib/salutation";

const styles = StyleSheet.create({
  page: { padding: 42, paddingBottom: 60, fontSize: 10, fontFamily: "Helvetica", color: "#1a1a1a" },
  // "fixed" hält die Fußzeile auf jeder Seite fest unten, unabhängig vom
  // normalen Textfluss — siehe ausführlicher Kommentar in documentPdf.tsx.
  footerMeta: {
    position: "absolute",
    bottom: 20,
    left: 42,
    right: 42,
    fontSize: 8,
    color: "#999",
    textAlign: "center",
    borderTop: "1px solid #eee",
    paddingTop: 6,
    flexDirection: "row",
    justifyContent: "space-between",
  },
  title: { fontSize: 18, fontFamily: "Helvetica-Bold", marginBottom: 4 },
  subtitle: { fontSize: 10, color: "#555", marginBottom: 24 },
  row: { flexDirection: "row", marginBottom: 3 },
  label: { width: 140, color: "#555" },
  value: { flex: 1 },
  p: { marginBottom: 6, lineHeight: 1.5 },
  tableHeader: { flexDirection: "row", borderBottom: "1px solid #333", paddingBottom: 4, marginBottom: 4 },
  tableRow: { flexDirection: "row", paddingVertical: 4, borderBottom: "1px solid #eee" },
  colDesc: { flex: 1 },
  colAmount: { width: 90, textAlign: "right" },
  totalsRow: { flexDirection: "row", justifyContent: "flex-end", marginTop: 4 },
  totalsLabel: { width: 110, textAlign: "right", color: "#555" },
  totalsValue: { width: 90, textAlign: "right" },
});

type InvoiceLocale = "de" | "en";

type InvoiceLabels = {
  invoice: string;
  invoiceDate: string;
  serviceDate: string;
  taxId: string;
  paymentReference: string;
  service: string;
  amount: string;
  discountCode: (code: string, amount: string) => string;
  manualDiscount: (note: string, amount: string) => string;
  totalAmount: string;
  netAmount: string;
  vat: (rate: number) => string;
  kleinunternehmer: string;
  paymentInstruction: (reference: string) => string;
  recipient: string;
  iban: string;
  bic: string;
  bank: string;
  paid: string;
};

const LABELS: Record<InvoiceLocale, InvoiceLabels> = {
  de: {
    invoice: "Rechnung",
    invoiceDate: "Rechnungsdatum",
    serviceDate: "Leistungsdatum / -zeitraum",
    taxId: "Steuernummer",
    paymentReference: "Verwendungszweck",
    service: "Leistung",
    amount: "Betrag",
    discountCode: (code: string, amount: string) =>
      `Rabattcode ${code}: −${amount} bereits im ausgewiesenen Betrag berücksichtigt.`,
    manualDiscount: (note: string, amount: string) =>
      `Rabatt${note ? ` (${note})` : ""}: −${amount} bereits im ausgewiesenen Betrag berücksichtigt.`,
    totalAmount: "Gesamtbetrag",
    netAmount: "Nettobetrag",
    vat: (rate: number) => `USt. (${rate}%)`,
    kleinunternehmer: "Gemäß § 19 UStG wird keine Umsatzsteuer berechnet.",
    paymentInstruction: (reference: string) =>
      `Bitte überweisen Sie den Betrag innerhalb von 14 Tagen ohne Abzug unter Angabe des Verwendungszwecks ${reference} auf folgendes Konto:`,
    recipient: "Empfänger",
    iban: "IBAN",
    bic: "BIC",
    bank: "Bank",
    paid: "Der Rechnungsbetrag ist beglichen. Vielen Dank!",
  },
  en: {
    invoice: "Invoice",
    invoiceDate: "Invoice date",
    serviceDate: "Service date / period",
    taxId: "Tax number",
    paymentReference: "Payment reference",
    service: "Service",
    amount: "Amount",
    discountCode: (code: string, amount: string) =>
      `Discount code ${code}: −${amount} already reflected in the amount shown.`,
    manualDiscount: (note: string, amount: string) =>
      `Discount${note ? ` (${note})` : ""}: −${amount} already reflected in the amount shown.`,
    totalAmount: "Total amount",
    netAmount: "Net amount",
    vat: (rate: number) => `VAT (${rate}%)`,
    kleinunternehmer: "No VAT is charged pursuant to § 19 UStG (German small business regulation).",
    paymentInstruction: (reference: string) =>
      `Please transfer the amount within 14 days without deduction, quoting the reference ${reference}, to the following account:`,
    recipient: "Recipient",
    iban: "IBAN",
    bic: "BIC",
    bank: "Bank",
    paid: "This invoice has been paid in full. Thank you!",
  },
};

function Field({ label, value }: { label: string; value?: string }) {
  if (!value) return null;
  return (
    <View style={styles.row}>
      <Text style={styles.label}>{label}</Text>
      <Text style={styles.value}>{value}</Text>
    </View>
  );
}

const fmt = formatEUR;

function InvoicePage({ invoice, locale }: { invoice: InvoiceDoc; locale: InvoiceLocale }) {
  const t = LABELS[locale];
  const dateLocale = locale === "en" ? "en-GB" : "de-DE";

  return (
    <Page size="A4" style={styles.page}>
      <View style={{ flexDirection: "row", justifyContent: "space-between", marginBottom: 28 }}>
        <View>
          <Text style={{ fontFamily: "Helvetica-Bold", marginBottom: 2 }}>{invoice.businessName}</Text>
          {invoice.businessLegalName && invoice.businessLegalName !== invoice.businessName && (
            <Text style={{ color: "#555", marginBottom: 2 }}>{invoice.businessLegalName}</Text>
          )}
          <Text style={{ color: "#555" }}>
            {formatAddress({
              street: invoice.businessStreet,
              postCode: invoice.businessPostCode,
              city: invoice.businessCity,
              countryCode: invoice.businessCountryCode,
            })}
          </Text>
        </View>
        <View>
          <Text style={{ fontFamily: "Helvetica-Bold", marginBottom: 2 }}>
            {formatNameWithSalutation(invoice.clientSalutation, invoice.clientName)}
          </Text>
          <Text style={{ color: "#555" }}>
            {formatAddress({
              street: invoice.clientStreet,
              postCode: invoice.clientPostCode,
              city: invoice.clientCity,
              countryCode: invoice.clientCountryCode,
            })}
          </Text>
        </View>
      </View>

      <Text style={styles.title}>
        {t.invoice} {invoice.number}
      </Text>
      <Text style={styles.subtitle}>{invoice.businessName}</Text>

      <Field label={t.invoiceDate} value={new Date(invoice.issueDate).toLocaleDateString(dateLocale)} />
      <Field label={t.serviceDate} value={invoice.serviceDate} />
      <Field label={t.taxId} value={invoice.businessTaxId} />
      <Field label={t.paymentReference} value={invoice.paymentReference} />

      <View style={{ marginTop: 20 }}>
        <View style={styles.tableHeader}>
          <Text style={[styles.colDesc, { fontFamily: "Helvetica-Bold" }]}>{t.service}</Text>
          <Text style={[styles.colAmount, { fontFamily: "Helvetica-Bold" }]}>{t.amount}</Text>
        </View>
        <View style={styles.tableRow}>
          <Text style={styles.colDesc}>{invoice.description}</Text>
          <Text style={styles.colAmount}>{fmt(invoice.netAmount)}</Text>
        </View>
      </View>

      {invoice.discountAmount > 0 && (
        <Text style={{ ...styles.p, marginTop: 8, fontSize: 8, color: "#777" }}>
          {t.discountCode(invoice.discountCode, fmt(invoice.discountAmount))}
        </Text>
      )}
      {invoice.manualDiscountAmount > 0 && (
        <Text style={{ ...styles.p, marginTop: 4, fontSize: 8, color: "#777" }}>
          {t.manualDiscount(invoice.manualDiscountNote, fmt(invoice.manualDiscountAmount))}
        </Text>
      )}

      {invoice.kleinunternehmer ? (
        <>
          <View style={styles.totalsRow}>
            <Text style={styles.totalsLabel}>{t.totalAmount}</Text>
            <Text style={[styles.totalsValue, { fontFamily: "Helvetica-Bold" }]}>{fmt(invoice.totalAmount)}</Text>
          </View>
          <Text style={{ ...styles.p, marginTop: 16, fontSize: 8, color: "#777" }}>{t.kleinunternehmer}</Text>
        </>
      ) : (
        <>
          <View style={styles.totalsRow}>
            <Text style={styles.totalsLabel}>{t.netAmount}</Text>
            <Text style={styles.totalsValue}>{fmt(invoice.netAmount)}</Text>
          </View>
          <View style={styles.totalsRow}>
            <Text style={styles.totalsLabel}>{t.vat(invoice.vatRate)}</Text>
            <Text style={styles.totalsValue}>{fmt(invoice.vatAmount)}</Text>
          </View>
          <View style={styles.totalsRow}>
            <Text style={[styles.totalsLabel, { fontFamily: "Helvetica-Bold" }]}>{t.totalAmount}</Text>
            <Text style={[styles.totalsValue, { fontFamily: "Helvetica-Bold" }]}>{fmt(invoice.totalAmount)}</Text>
          </View>
        </>
      )}

      <Text style={{ ...styles.p, marginTop: 24 }}>{t.paymentInstruction(invoice.paymentReference)}</Text>
      <Field label={t.recipient} value={invoice.accountHolderName || invoice.businessName} />
      <Field label={t.iban} value={invoice.businessIban} />
      <Field label={t.bic} value={invoice.businessBic} />
      <Field label={t.bank} value={invoice.businessBankName} />

      {invoice.status === "paid" && (
        <Text style={{ ...styles.p, marginTop: 20, color: "#059669", fontFamily: "Helvetica-Bold" }}>{t.paid}</Text>
      )}

      <View style={styles.footerMeta} fixed>
        <Text>
          {t.invoice} {invoice.number}
        </Text>
        <Text render={({ pageNumber, totalPages }) => `${locale === "en" ? "Page" : "Seite"} ${pageNumber} ${locale === "en" ? "of" : "von"} ${totalPages}`} />
      </View>
    </Page>
  );
}

export async function renderInvoicePdf(invoice: InvoiceDoc, locale: InvoiceLocale = "de"): Promise<Buffer> {
  const doc = (
    <Document>
      <InvoicePage invoice={invoice} locale={locale} />
    </Document>
  );
  return renderToBuffer(doc);
}
