"use client"

import { useEffect, useMemo, useState } from "react"
import Link from "next/link"
import {
  AlertTriangle,
  BadgeDollarSign,
  Boxes,
  Clock,
  ClipboardList,
  ListChecks,
  PackageCheck,
  ScrollText,
  Send,
} from "lucide-react"

import { dashboardApi } from "@/lib/api/dashboard"
import { stockApi } from "@/lib/api/stock"
import { warehousesApi } from "@/lib/api/warehouses"
import { errorMessage } from "@/lib/error-map"
import { cn } from "@/lib/utils"
import { DashboardStats } from "@/types/dashboard"
import { LedgerEntry } from "@/types/stock"
import { Warehouse } from "@/types/master-data"
import { StatCard } from "@/components/ui/stat-card"
import { Skeleton } from "@/components/ui/skeleton"
import { Badge } from "@/components/ui/badge"
import { buttonVariants } from "@/components/ui/button"
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table"
import BarChart from "@/components/ui/bar-chart"
import LineChart from "@/components/ui/line-chart"

const TREND_DAYS = 14

function isoDate(d: Date) {
  return d.toISOString().slice(0, 10)
}

// Shown only when the last TREND_DAYS days have no real ledger activity, so the
// chart isn't a flat zero line before there's any real movement to plot.
const SAMPLE_TREND_IN = [42, 58, 35, 70, 64, 30, 20, 85, 46, 55, 38, 62, 48, 72]
const SAMPLE_TREND_OUT = [30, 40, 45, 38, 50, 22, 15, 60, 33, 47, 28, 44, 36, 58]

export default function DashboardPage() {
  const [stats, setStats] = useState<DashboardStats | null>(null)
  const [movements, setMovements] = useState<LedgerEntry[] | null>(null)
  const [trend, setTrend] = useState<LedgerEntry[] | null>(null)
  const [warehouses, setWarehouses] = useState<Warehouse[] | null>(null)
  const [error, setError] = useState<string | null>(null)

  useEffect(() => {
    let cancelled = false

    const from = new Date()
    from.setDate(from.getDate() - (TREND_DAYS - 1))

    Promise.all([
      dashboardApi.stats(),
      stockApi.ledger({ page: 1, pageSize: 5 }),
      stockApi.ledger({ from: isoDate(from), page: 1, pageSize: 200 }),
      warehousesApi.list(),
    ])
      .then(([statsRes, ledger, trendRes, warehousesRes]) => {
        if (cancelled) return
        setStats(statsRes)
        setMovements(ledger.items)
        setTrend(trendRes.items)
        setWarehouses(warehousesRes.items)
      })
      .catch((err) => {
        if (!cancelled) setError(errorMessage(err))
      })

    return () => {
      cancelled = true
    }
  }, [])

  const warehousesById = useMemo(() => new Map((warehouses ?? []).map((w) => [w.warehouseId, w])), [warehouses])

  // Last TREND_DAYS days, oldest first, each bucket summing In/Out qty for that date.
  const movementTrend = useMemo(() => {
    const days: string[] = []
    const cursor = new Date()
    cursor.setDate(cursor.getDate() - (TREND_DAYS - 1))
    for (let i = 0; i < TREND_DAYS; i++) {
      days.push(isoDate(cursor))
      cursor.setDate(cursor.getDate() + 1)
    }

    const labels = days.map((d) => new Date(d).toLocaleDateString(undefined, { day: "numeric", month: "short" }))

    if (!trend || trend.length === 0) {
      return { labels, inData: SAMPLE_TREND_IN, outData: SAMPLE_TREND_OUT }
    }

    const inByDay = new Map(days.map((d) => [d, 0]))
    const outByDay = new Map(days.map((d) => [d, 0]))
    for (const entry of trend) {
      const day = entry.createdAt.slice(0, 10)
      const bucket = entry.direction === "In" ? inByDay : outByDay
      if (bucket.has(day)) bucket.set(day, (bucket.get(day) ?? 0) + entry.qtyBase)
    }

    return {
      labels,
      inData: days.map((d) => inByDay.get(d) ?? 0),
      outData: days.map((d) => outByDay.get(d) ?? 0),
    }
  }, [trend])

  const loaded = stats && movements && trend && warehouses

  return (
    <div className="flex flex-col gap-6">
      <div>
        <h1 className="text-base font-bold text-foreground sm:text-lg">Dashboard</h1>
        <p className="text-xs text-muted-foreground sm:text-sm">Overview of stock, receiving and procurement.</p>
      </div>

      {error && (
        <div role="alert" className="rounded-lg border border-destructive/30 bg-destructive/5 p-4 text-sm text-destructive">
          {error}
        </div>
      )}

      <div className="grid grid-cols-1 gap-2 sm:grid-cols-2 sm:gap-3 lg:grid-cols-4">
        {loaded ? (
          <>
            <Link href="/dashboard/stock/reorder-alerts">
              <StatCard label="Low Stock Alerts" value={stats.lowStockAlerts} icon={AlertTriangle} />
            </Link>
            <Link href="/dashboard/stock/enquiry">
              <StatCard label="Stock On-Hand" value={stats.onHandTotal} icon={Boxes} />
            </Link>
            <Link href="/dashboard/procurement/purchase-orders">
              <StatCard label="Pending Approval POs" value={stats.pendingApprovalPurchaseOrders} icon={Clock} />
            </Link>
            <Link href="/dashboard/receiving/grn">
              <StatCard label="Pending GRNs" value={stats.pendingGrns} icon={PackageCheck} />
            </Link>
            <Link href="/dashboard/procurement/requisitions">
              <StatCard label="Open Requisitions" value={stats.openRequisitions} icon={ClipboardList} />
            </Link>
            <Link href="/dashboard/stock/counts">
              <StatCard label="Open Counts" value={stats.pendingCounts} icon={ListChecks} />
            </Link>
            <Link href="/dashboard/procurement/rfqs">
              <StatCard label="Active RFQs" value={stats.openRfqs} icon={Send} />
            </Link>
          </>
        ) : (
          !error && Array.from({ length: 7 }).map((_, i) => <Skeleton key={i} className="h-24 rounded-2xl" />)
        )}
      </div>

      <div className="rounded-2xl bg-card p-4 shadow-sm ring-1 ring-foreground/10 sm:p-5">
        <div className="mb-4 flex flex-col items-start gap-2 sm:flex-row sm:items-center sm:justify-between">
          <h2 className="flex items-center gap-2 text-sm font-bold tracking-tight text-foreground sm:text-base">
            <BadgeDollarSign className="size-4 shrink-0 text-primary" />
            Stock Valuation by Warehouse
          </h2>
          <Link href="/dashboard/stock/valuation" className={cn(buttonVariants({ variant: "ghost", size: "sm" }))}>
            View details
          </Link>
        </div>

        {loaded ? (
          (stats.stockValuationByWarehouse ?? []).length > 0 ? (
            <div className="h-52 sm:h-64">
              <BarChart
                labels={stats.stockValuationByWarehouse.map(
                  (w) => warehousesById.get(w.warehouseId)?.code ?? `#${w.warehouseId}`
                )}
                datasets={[
                  {
                    label: "Stock Value (LKR)",
                    data: stats.stockValuationByWarehouse.map((w) => w.total),
                    backgroundColor: "#6366f1",
                  },
                ]}
              />
            </div>
          ) : (
            <p className="py-6 text-center text-sm text-muted-foreground">No stock on hand yet.</p>
          )
        ) : (
          !error && <Skeleton className="h-52 rounded-lg sm:h-64" />
        )}
      </div>

      <div className="rounded-2xl bg-card p-4 shadow-sm ring-1 ring-foreground/10 sm:p-5">
        <div className="mb-4 flex items-center gap-2">
          <ScrollText className="size-4 shrink-0 text-primary" />
          <h2 className="text-sm font-bold tracking-tight text-foreground sm:text-base">
            Stock Movement Trend (last {TREND_DAYS} days)
          </h2>
        </div>

        {loaded ? (
          <div className="h-52 sm:h-64">
            <LineChart
              labels={movementTrend.labels}
              datasets={[
                { label: "In", data: movementTrend.inData, borderColor: "#22c55e", backgroundColor: "rgba(34, 197, 94, 0.12)" },
                { label: "Out", data: movementTrend.outData, borderColor: "#ef4444", backgroundColor: "rgba(239, 68, 68, 0.12)" },
              ]}
            />
          </div>
        ) : (
          !error && <Skeleton className="h-52 rounded-lg sm:h-64" />
        )}
      </div>

      <div className="rounded-2xl bg-card p-4 shadow-sm ring-1 ring-foreground/10 sm:p-5">
        <div className="mb-4 flex flex-col items-start gap-2 sm:flex-row sm:items-center sm:justify-between">
          <h2 className="flex items-center gap-2 text-sm font-bold tracking-tight text-foreground sm:text-base">
            <ScrollText className="size-4 shrink-0 text-primary" />
            Recent Stock Movements
          </h2>
          <Link href="/dashboard/stock/ledger" className={cn(buttonVariants({ variant: "ghost", size: "sm" }))}>
            View all
          </Link>
        </div>

        {loaded ? (
          movements.length > 0 ? (
            <Table>
              <TableHeader>
                <TableRow>
                  <TableHead>Item</TableHead>
                  <TableHead>Warehouse</TableHead>
                  <TableHead>Direction</TableHead>
                  <TableHead>Qty</TableHead>
                  <TableHead>Source</TableHead>
                  <TableHead className="text-right">Date</TableHead>
                </TableRow>
              </TableHeader>
              <TableBody>
                {movements.map((entry) => (
                  <TableRow key={entry.ledgerId}>
                    <TableCell className="font-medium text-foreground">#{entry.itemId}</TableCell>
                    <TableCell className="text-muted-foreground">
                      {warehousesById.get(entry.warehouseId)?.code ?? `#${entry.warehouseId}`}
                    </TableCell>
                    <TableCell>
                      <Badge
                        variant="outline"
                        className={cn(
                          "h-6 w-16 justify-center text-xs",
                          entry.direction === "In"
                            ? "border-transparent bg-success/10 text-success"
                            : "border-transparent bg-destructive/10 text-destructive"
                        )}
                      >
                        {entry.direction}
                      </Badge>
                    </TableCell>
                    <TableCell className="text-muted-foreground">{entry.qtyBase}</TableCell>
                    <TableCell className="text-muted-foreground">
                      {entry.sourceDocType} #{entry.sourceDocId}
                    </TableCell>
                    <TableCell className="text-right text-muted-foreground">
                      {new Date(entry.createdAt).toLocaleDateString()}
                    </TableCell>
                  </TableRow>
                ))}
              </TableBody>
            </Table>
          ) : (
            <p className="py-6 text-center text-sm text-muted-foreground">No stock movements yet.</p>
          )
        ) : (
          !error && (
            <div className="flex flex-col gap-2">
              {Array.from({ length: 5 }).map((_, i) => (
                <Skeleton key={i} className="h-10 rounded-lg" />
              ))}
            </div>
          )
        )}
      </div>
    </div>
  )
}
