"use client";

import {
  createFinanceTransactionRecord,
  deleteFinanceTransactionRecord,
  updateFinanceTransactionRecord,
} from "@/app/(dashboard)/finance/actions";
import { Badge, Button, Card, CardContent, Input, Label, Textarea } from "poyraz-ui/atoms";
import {
  Dialog,
  DialogContent,
  DialogDescription,
  DialogFooter,
  DialogHeader,
  DialogTitle,
  DialogTrigger,
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
  toast,
} from "poyraz-ui/molecules";
import {
  ArrowDownRight,
  ArrowUpRight,
  Pencil,
  Plus,
  Trash2,
  Wallet,
  Brain,
  Loader2,
} from "lucide-react";
import { useMemo, useState } from "react";

export type FinanceRelationOption = {
  id: string;
  name: string;
  client_id?: string | null;
};

export type FinanceTransactionItem = {
  id: string;
  type: "income" | "expense";
  amount: number;
  currency: string;
  transaction_date: string;
  category: string | null;
  payment_status: "planned" | "pending" | "paid" | "cancelled";
  client_id: string | null;
  project_id: string | null;
  clientName: string | null;
  projectName: string | null;
  description: string | null;
};

const typeLabels = {
  income: "Gelir",
  expense: "Gider",
};

const paymentStatusLabels = {
  planned: "Planlandı",
  pending: "Bekliyor",
  paid: "Ödendi",
  cancelled: "İptal edildi",
};

const paymentStatusClasses = {
  planned: "border-blue-200 bg-blue-50 text-blue-700",
  pending: "border-amber-200 bg-amber-50 text-amber-700",
  paid: "border-emerald-200 bg-emerald-50 text-emerald-700",
  cancelled: "border-zinc-200 bg-zinc-50 text-zinc-700",
};

const currencyOptions = [
  { value: "USD", label: "Dolar (USD)" },
  { value: "EUR", label: "Euro (EUR)" },
  { value: "TRY", label: "Türk lirası (TRY)" },
  { value: "GBP", label: "Sterlin (GBP)" },
  { value: "CAD", label: "Kanada doları (CAD)" },
  { value: "AUD", label: "Avustralya doları (AUD)" },
];

type FinanceClientProps = {
  transactions: FinanceTransactionItem[];
  clients: FinanceRelationOption[];
  projects: FinanceRelationOption[];
};

export function FinanceClient({ transactions, clients, projects }: FinanceClientProps) {
  const [query, setQuery] = useState("");
  const [monthFilter, setMonthFilter] = useState(() => new Date().toISOString().slice(0, 7));
  const normalizedQuery = query.trim().toLowerCase();
  const filteredByMonth = transactions.filter((transaction) =>
    transaction.transaction_date.startsWith(monthFilter),
  );
  const filteredTransactions = normalizedQuery
    ? filteredByMonth.filter((transaction) =>
        [
          transaction.description,
          transaction.category,
          transaction.clientName,
          transaction.projectName,
          typeLabels[transaction.type],
        ]
          .filter(Boolean)
          .some((value) => value!.toLowerCase().includes(normalizedQuery)),
      )
    : filteredByMonth;

  const summary = useMemo(() => calculateSummary(filteredByMonth), [filteredByMonth]);
  const categoryBreakdown = useMemo(() => calculateExpenseCategories(filteredByMonth), [filteredByMonth]);

  return (
    <div className="mx-auto flex max-w-7xl flex-col gap-6">
      <div className="flex flex-col gap-4 border-b border-border pb-5 lg:flex-row lg:items-end lg:justify-between">
        <div>
          <h1 className="text-3xl font-semibold tracking-normal text-foreground">
            Finans işlemleri
          </h1>
          <p className="mt-1 max-w-2xl text-sm text-muted-foreground">
            Gelir, gider, ödeme durumu ve proje/müşteri bağlantılarını takip et.
          </p>
        </div>
        <div className="flex gap-2">
          <AIFinanceDialog />
          <FinanceDialog mode="create" clients={clients} projects={projects} />
        </div>
      </div>

      <div className="grid gap-3 md:grid-cols-3 lg:grid-cols-6">
        <StatCard label="Aylık gelir" value={formatCurrency(summary.income)} tone="green" />
        <StatCard label="Aylık gider" value={formatCurrency(summary.expense)} tone="rose" />
        <StatCard label="Brüt kazanç" value={formatCurrency(summary.net)} tone="primary" />
        <StatCard label="KDV Tahmini (%20)" value={formatCurrency(summary.tax)} tone="amber" />
        <StatCard label="Vergi Sonrası Net" value={formatCurrency(summary.afterTax)} tone="green" />
        <StatCard label="Bekleyen" value={formatCurrency(summary.pending)} tone="amber" />
      </div>

      <div className="grid gap-6 lg:grid-cols-[1fr_320px]">
        <Card>
          <CardContent className="space-y-4 p-4">
            <div className="flex flex-col gap-3 lg:flex-row lg:items-center lg:justify-between">
              <div>
                <h2 className="text-base font-semibold text-foreground">İşlem listesi</h2>
                <p className="text-sm text-muted-foreground">
                  {filteredTransactions.length} kayıt görüntüleniyor.
                </p>
              </div>
              <div className="flex flex-col gap-2 sm:flex-row">
                <Input
                  value={query}
                  onChange={(event) => setQuery(event.target.value)}
                  placeholder="Kategori, müşteri, proje veya açıklama ara"
                  className="sm:w-80"
                />
                <Input
                  type="month"
                  value={monthFilter}
                  onChange={(event) => setMonthFilter(event.target.value)}
                  className="sm:w-44"
                />
              </div>
            </div>

            {filteredTransactions.length > 0 ? (
              <div className="overflow-x-auto rounded-sm border border-border">
                <div className="min-w-[800px]">
                  <div className="grid grid-cols-[1.4fr_0.8fr_0.8fr_0.8fr_1fr] gap-4 border-b border-border bg-muted/40 px-4 py-3 text-xs font-medium uppercase text-muted-foreground">
                    <span>İşlem</span>
                    <span>Tarih</span>
                    <span>Tutar</span>
                    <span>Durum</span>
                    <span className="text-right">İşlem</span>
                  </div>
                  <div className="divide-y divide-border">
                  {filteredTransactions.map((transaction) => (
                    <TransactionRow
                      key={transaction.id}
                      transaction={transaction}
                      clients={clients}
                      projects={projects}
                    />
                  ))}
                  </div>
                </div>
              </div>
            ) : (
              <EmptyState hasQuery={Boolean(normalizedQuery)} />
            )}
          </CardContent>
        </Card>

        <Card>
          <CardContent className="space-y-4 p-4">
            <div>
              <h2 className="text-base font-semibold text-foreground">Gider kategorileri</h2>
              <p className="text-sm text-muted-foreground">Aylık gider dağılımı</p>
            </div>
            {categoryBreakdown.length > 0 ? (
              <div className="space-y-3">
                {categoryBreakdown.map((item) => (
                  <div key={item.category} className="space-y-1">
                    <div className="flex justify-between text-sm">
                      <span className="text-muted-foreground">{item.category}</span>
                      <span className="font-medium text-foreground">{formatCurrency(item.amount)}</span>
                    </div>
                    <div className="h-2 rounded-full bg-muted">
                      <div
                        className="h-full rounded-full bg-primary"
                        style={{ width: `${item.percent}%` }}
                      />
                    </div>
                  </div>
                ))}
              </div>
            ) : (
              <p className="text-sm text-muted-foreground">Bu ay gider kaydı yok.</p>
            )}
          </CardContent>
        </Card>
      </div>
    </div>
  );
}

function TransactionRow({
  transaction,
  clients,
  projects,
}: {
  transaction: FinanceTransactionItem;
  clients: FinanceRelationOption[];
  projects: FinanceRelationOption[];
}) {
  const isIncome = transaction.type === "income";

  return (
    <div className="grid gap-4 px-4 py-4 grid-cols-[1.4fr_0.8fr_0.8fr_0.8fr_1fr] items-center">
      <div className="flex min-w-0 items-start gap-3">
        <div className={isIncome ? "rounded-sm bg-emerald-50 p-2 text-emerald-700" : "rounded-sm bg-rose-50 p-2 text-rose-700"}>
          {isIncome ? <ArrowUpRight className="h-4 w-4" /> : <ArrowDownRight className="h-4 w-4" />}
        </div>
        <div className="min-w-0">
          <div className="font-medium text-foreground">
            {transaction.description || typeLabels[transaction.type]}
          </div>
          <div className="truncate text-sm text-muted-foreground">
            {transaction.category || "Kategori yok"} · {transaction.projectName || transaction.clientName || "Bağlantı yok"}
          </div>
        </div>
      </div>
      <div className="text-sm text-muted-foreground">{formatDate(transaction.transaction_date)}</div>
      <div className={isIncome ? "font-semibold text-emerald-700" : "font-semibold text-rose-700"}>
        {isIncome ? "+" : "-"}
        {formatCurrency(transaction.amount, transaction.currency)}
      </div>
      <div>
        <Badge className={paymentStatusClasses[transaction.payment_status]}>
          {paymentStatusLabels[transaction.payment_status]}
        </Badge>
      </div>
      <div className="flex justify-end gap-2">
        <FinanceDialog mode="edit" transaction={transaction} clients={clients} projects={projects} />
        <form action={deleteFinanceTransactionRecord}>
          <input type="hidden" name="id" value={transaction.id} />
          <Button type="submit" variant="outline" className="h-9 gap-2 text-rose-600">
            <Trash2 className="h-4 w-4" />
            Sil
          </Button>
        </form>
      </div>
    </div>
  );
}

function FinanceDialog({
  mode,
  transaction,
  clients,
  projects,
}: {
  mode: "create" | "edit";
  transaction?: FinanceTransactionItem;
  clients: FinanceRelationOption[];
  projects: FinanceRelationOption[];
}) {
  const [open, setOpen] = useState(false);
  const [isSubmitting, setIsSubmitting] = useState(false);
  const action = mode === "create" ? createFinanceTransactionRecord : updateFinanceTransactionRecord;

  async function handleSubmit(formData: FormData) {
    setIsSubmitting(true);
    try {
      await action(formData);
      setOpen(false);
      toast.success(mode === "create" ? "İşlem eklendi." : "İşlem güncellendi.");
    } catch (error) {
      toast.error(
        error instanceof Error
          ? error.message
          : "Finans işlemi kaydedilirken beklenmeyen bir hata oluştu.",
      );
    } finally {
      setIsSubmitting(false);
    }
  }

  return (
    <Dialog open={open} onOpenChange={setOpen}>
      <DialogTrigger asChild>
        <Button variant={mode === "create" ? "default" : "outline"} className="h-9 gap-2">
          {mode === "create" ? <Plus className="h-4 w-4" /> : <Pencil className="h-4 w-4" />}
          {mode === "create" ? "İşlem ekle" : "Düzenle"}
        </Button>
      </DialogTrigger>
      <DialogContent className="flex max-h-[calc(100dvh-2rem)] w-[calc(100vw-2rem)] flex-col overflow-hidden p-0 sm:max-h-[min(680px,calc(100dvh-4rem))] sm:max-w-xl data-[state=open]:animate-in data-[state=open]:fade-in-0 data-[state=open]:zoom-in-95">
        <form action={handleSubmit} className="flex min-h-0 flex-1 flex-col overflow-hidden">
          {transaction ? <input type="hidden" name="id" value={transaction.id} /> : null}
          <DialogHeader className="shrink-0 px-5 pb-4 pt-5 pr-12">
            <DialogTitle>{mode === "create" ? "Yeni finans işlemi" : "Finans işlemini düzenle"}</DialogTitle>
            <DialogDescription>Gelir veya gider kaydını müşteri/proje bağlantısıyla kaydet.</DialogDescription>
          </DialogHeader>
          <div className="tiny-scrollbar min-h-0 flex-1 overflow-y-auto px-5 pb-5">
            <FinanceFormFields transaction={transaction} clients={clients} projects={projects} />
          </div>
          <DialogFooter className="shrink-0 border-t border-border bg-background p-5">
            <Button type="submit" disabled={isSubmitting} className="w-full gap-2 sm:w-auto">
              {mode === "create" ? <Plus className="h-4 w-4" /> : <Pencil className="h-4 w-4" />}
              {isSubmitting ? "Kaydediliyor" : mode === "create" ? "İşlemi ekle" : "Değişiklikleri kaydet"}
            </Button>
          </DialogFooter>
        </form>
      </DialogContent>
    </Dialog>
  );
}

function FinanceFormFields({
  transaction,
  clients,
  projects,
}: {
  transaction?: FinanceTransactionItem;
  clients: FinanceRelationOption[];
  projects: FinanceRelationOption[];
}) {
  const [clientId, setClientId] = useState(transaction?.client_id || "__none");
  const [projectId, setProjectId] = useState(transaction?.project_id || "__none");
  const selectedProject =
    projectId === "__none" ? null : projects.find((project) => project.id === projectId) || null;
  const shouldLockClient = Boolean(selectedProject);
  const filteredProjects =
    clientId === "__none" || shouldLockClient
      ? projects
      : projects.filter((project) => project.client_id === clientId);
  const currencyValue = transaction?.currency || "USD";
  const hasCustomCurrency = !currencyOptions.some((currency) => currency.value === currencyValue);

  function handleClientChange(nextClientId: string) {
    setClientId(nextClientId);

    if (
      projectId !== "__none" &&
      nextClientId !== "__none" &&
      !projects.some((project) => project.id === projectId && project.client_id === nextClientId)
    ) {
      setProjectId("__none");
    }
  }

  function handleProjectChange(nextProjectId: string) {
    setProjectId(nextProjectId);

    if (nextProjectId === "__none") {
      return;
    }

    const nextProject = projects.find((project) => project.id === nextProjectId);
    setClientId(nextProject?.client_id || "__none");
  }

  return (
    <div className="grid gap-4">
      <div className="grid gap-4 md:grid-cols-2">
        <SelectField name="type" label="Tip" defaultValue={transaction?.type || "income"}>
          <SelectItem value="income">Gelir</SelectItem>
          <SelectItem value="expense">Gider</SelectItem>
        </SelectField>
        <SelectField name="payment_status" label="Ödeme durumu" defaultValue={transaction?.payment_status || "planned"}>
          <SelectItem value="planned">Planlandı</SelectItem>
          <SelectItem value="pending">Bekliyor</SelectItem>
          <SelectItem value="paid">Ödendi</SelectItem>
          <SelectItem value="cancelled">İptal edildi</SelectItem>
        </SelectField>
      </div>
      <div className="grid gap-4 md:grid-cols-3">
        <div className="grid gap-2">
          <Label>Tutar</Label>
          <Input name="amount" type="number" min="0" step="0.01" required defaultValue={transaction?.amount ?? ""} />
        </div>
        <div className="grid gap-2">
          <Label>Para birimi</Label>
          <Select name="currency" defaultValue={currencyValue}>
            <SelectTrigger>
              <SelectValue placeholder="Para birimi seç" />
            </SelectTrigger>
            <SelectContent>
              {currencyOptions.map((currency) => (
                <SelectItem key={currency.value} value={currency.value}>
                  {currency.label}
                </SelectItem>
              ))}
              {hasCustomCurrency ? (
                <SelectItem value={currencyValue}>{currencyValue}</SelectItem>
              ) : null}
            </SelectContent>
          </Select>
        </div>
        <div className="grid gap-2">
          <Label>Tarih</Label>
          <Input name="transaction_date" type="date" defaultValue={transaction?.transaction_date || new Date().toISOString().slice(0, 10)} />
        </div>
      </div>
      <div className="grid gap-2">
        <Label>Kategori</Label>
        <Input name="category" defaultValue={transaction?.category || ""} placeholder="Örn. Yazılım, müşteri ödemesi, vergi" />
      </div>
      <div className="grid gap-4 md:grid-cols-2">
        <div className="grid gap-2">
          <Label>Müşteri</Label>
          {shouldLockClient ? <input type="hidden" name="client_id" value={clientId} /> : null}
          <Select
            name="client_id"
            value={clientId}
            onValueChange={handleClientChange}
            disabled={shouldLockClient}
          >
            <SelectTrigger>
              <SelectValue placeholder="Müşteri seç" />
            </SelectTrigger>
            <SelectContent>
              <SelectItem value="__none">Müşteri yok</SelectItem>
              {clients.map((client) => (
                <SelectItem key={client.id} value={client.id}>
                  {client.name}
                </SelectItem>
              ))}
            </SelectContent>
          </Select>
        </div>
        <div className="grid gap-2">
          <Label>Proje</Label>
          <Select name="project_id" value={projectId} onValueChange={handleProjectChange}>
            <SelectTrigger>
              <SelectValue placeholder="Proje seç" />
            </SelectTrigger>
            <SelectContent>
              <SelectItem value="__none">Proje yok</SelectItem>
              {filteredProjects.map((project) => (
                <SelectItem key={project.id} value={project.id}>
                  {project.name}
                </SelectItem>
              ))}
            </SelectContent>
          </Select>
        </div>
      </div>
      <div className="grid gap-2">
        <Label>Açıklama</Label>
        <Textarea name="description" defaultValue={transaction?.description || ""} rows={3} />
      </div>
    </div>
  );
}

function SelectField({ name, label, defaultValue, children }: { name: string; label: string; defaultValue: string; children: React.ReactNode }) {
  return (
    <div className="grid gap-2">
      <Label>{label}</Label>
      <Select name={name} defaultValue={defaultValue}>
        <SelectTrigger><SelectValue placeholder={`${label} seç`} /></SelectTrigger>
        <SelectContent>{children}</SelectContent>
      </Select>
    </div>
  );
}

function StatCard({ label, value, tone }: { label: string; value: string; tone: "green" | "rose" | "primary" | "amber" }) {
  const toneClass = {
    green: "bg-emerald-50 text-emerald-700",
    rose: "bg-rose-50 text-rose-700",
    primary: "bg-primary/10 text-primary",
    amber: "bg-amber-50 text-amber-700",
  }[tone];

  return (
    <Card>
      <CardContent className="flex items-center justify-between gap-3 p-4">
        <div>
          <p className="text-sm text-muted-foreground">{label}</p>
          <p className="mt-1 text-2xl font-semibold text-foreground">{value}</p>
        </div>
        <div className={`flex h-10 w-10 items-center justify-center rounded-sm ${toneClass}`}>
          <Wallet className="h-5 w-5" />
        </div>
      </CardContent>
    </Card>
  );
}

function EmptyState({ hasQuery }: { hasQuery: boolean }) {
  return (
    <div className="flex min-h-72 flex-col items-center justify-center rounded-sm border border-dashed border-border bg-muted/20 p-8 text-center">
      <Wallet className="h-10 w-10 text-muted-foreground" />
      <h3 className="mt-4 text-lg font-semibold text-foreground">
        {hasQuery ? "Aramana uygun işlem yok" : "Henüz finans işlemi eklenmedi"}
      </h3>
      <p className="mt-2 max-w-md text-sm text-muted-foreground">
        {hasQuery
          ? "Arama metnini sadeleştirerek tekrar deneyebilirsin."
          : "İlk gelir veya gider kaydını ekleyerek aylık finans özetini oluşturmaya başlayabilirsin."}
      </p>
    </div>
  );
}

function calculateSummary(transactions: FinanceTransactionItem[]) {
  return transactions.reduce(
    (summary, transaction) => {
      if (transaction.type === "income" && transaction.payment_status === "paid") {
        summary.income += transaction.amount;
      }
      if (transaction.type === "expense" && transaction.payment_status === "paid") {
        summary.expense += transaction.amount;
      }
      if (transaction.payment_status === "pending" || transaction.payment_status === "planned") {
        summary.pending += transaction.amount;
      }
      summary.net = summary.income - summary.expense;
      summary.tax = summary.income * 0.20; // 20% KDV/Vergi tahmini
      summary.afterTax = summary.net - summary.tax;
      return summary;
    },
    { income: 0, expense: 0, net: 0, tax: 0, afterTax: 0, pending: 0 },
  );
}

function formatMessageContent(text: string) {
  if (!text) return null;
  const lines = text.split("\n");
  return lines.map((line, i) => (
    <span key={i}>
      {line.split(/(\*\*.*?\*\*|\*.*?\*)/g).map((part, j) => {
        if (part.startsWith("**") && part.endsWith("**")) {
          return (
            <strong key={j} className="font-semibold text-foreground">
              {part.slice(2, -2)}
            </strong>
          );
        }
        if (part.startsWith("*") && part.endsWith("*")) {
          return <em key={j}>{part.slice(1, -1)}</em>;
        }
        return <span key={j}>{part}</span>;
      })}
      {i !== lines.length - 1 && <br />}
    </span>
  ));
}

function AIFinanceDialog() {
  const [open, setOpen] = useState(false);
  const [loading, setLoading] = useState(false);
  const [result, setResult] = useState<string | null>(null);

  const handleAnalyze = async () => {
    setLoading(true);
    setResult(null);
    try {
      const res = await fetch("/api/finance-analysis", { method: "POST" });
      const data = await res.json();
      if (!res.ok) {
        throw new Error(data.error || "Bilinmeyen bir hata oluştu.");
      }
      setResult(data.text);
    } catch (err: any) {
      setResult("Hata: " + err.message);
    } finally {
      setLoading(false);
    }
  };

  return (
    <Dialog open={open} onOpenChange={setOpen}>
      <DialogTrigger asChild>
        <Button variant="outline" className="gap-2 bg-indigo-50 text-indigo-700 border-indigo-200 hover:bg-indigo-100 hover:text-indigo-800">
          <Brain className="h-4 w-4" />
          AI Analizi
        </Button>
      </DialogTrigger>
      <DialogContent className="w-[calc(100vw-2rem)] sm:max-w-2xl max-h-[80vh] overflow-y-auto rounded-lg p-6">
        <DialogHeader>
          <DialogTitle className="flex items-center gap-2">
            <Brain className="h-5 w-5 text-indigo-600" />
            Yapay Zeka Finansal Yorumlama
          </DialogTitle>
          <DialogDescription>
            Son 30 günlük finansal kayıtlarınızı analiz edip size önerilerde bulunuyorum.
          </DialogDescription>
        </DialogHeader>

        <div className="py-4">
          {!result && !loading && (
            <div className="text-center py-10">
              <Button onClick={handleAnalyze} className="gap-2 bg-indigo-600 hover:bg-indigo-700 text-white">
                <Brain className="h-4 w-4" />
                Raporu Oluştur
              </Button>
            </div>
          )}

          {loading && (
            <div className="flex flex-col items-center justify-center py-10 space-y-4 text-indigo-600">
              <Loader2 className="h-8 w-8 animate-spin" />
              <p className="text-sm font-medium">Verileriniz analiz ediliyor...</p>
            </div>
          )}

          {result && (
            <div className="bg-muted/50 border border-border rounded-lg p-5 text-sm prose prose-sm dark:prose-invert max-w-none whitespace-pre-wrap">
              {formatMessageContent(result)}
            </div>
          )}
        </div>

        {result && (
          <DialogFooter className="gap-2 sm:gap-0">
            <Button variant="outline" onClick={() => setOpen(false)}>Kapat</Button>
            <Button variant="default" onClick={handleAnalyze} className="gap-2">
              <Brain className="h-4 w-4" />
              Yeniden Oluştur
            </Button>
          </DialogFooter>
        )}
      </DialogContent>
    </Dialog>
  );
}

function calculateExpenseCategories(transactions: FinanceTransactionItem[]) {
  const totals = new Map<string, number>();
  for (const transaction of transactions) {
    if (transaction.type !== "expense") continue;
    const category = transaction.category || "Kategori yok";
    totals.set(category, (totals.get(category) || 0) + transaction.amount);
  }

  const total = Array.from(totals.values()).reduce((sum, value) => sum + value, 0);
  return Array.from(totals.entries())
    .map(([category, amount]) => ({
      category,
      amount,
      percent: total ? Math.round((amount / total) * 100) : 0,
    }))
    .sort((a, b) => b.amount - a.amount)
    .slice(0, 6);
}

function formatCurrency(value: number, currency = "USD") {
  return new Intl.NumberFormat("tr-TR", {
    style: "currency",
    currency,
    maximumFractionDigits: 0,
  }).format(value);
}

function formatDate(value: string) {
  return new Intl.DateTimeFormat("tr-TR", {
    day: "2-digit",
    month: "short",
    year: "numeric",
  }).format(new Date(`${value}T00:00:00`));
}
