import type { Metadata } from "next";
import Link from "next/link";
import { notFound } from "next/navigation";
import { db } from "@/lib/db";
import { productCardInclude, variantAvailability, priceRange, productAvailability } from "@/lib/catalog";
import { batchState, STATE_LABEL, depositLabel, depositPerUnit, balanceDueDate, remainingCapacity } from "@/lib/preorder";
import { fmtDate, fmtWindow } from "@/lib/dates";
import { taka } from "@/lib/money";
import { ownerKey } from "@/lib/visitor";
import { getSettings } from "@/lib/settings";
import ProductView, { type VariantView } from "@/components/store/ProductView";
import ProductCard from "@/components/store/ProductCard";
import { Markdown } from "@/lib/markdown";

type Props = { params: Promise<{ slug: string }> };

const load = (slug: string) => db.product.findFirst({
  where: { slug, status: "PUBLISHED" },
  include: { category: true, images: { orderBy: { sortOrder: "asc" } }, variants: { where: { active: true }, include: { batch: true }, orderBy: { sortOrder: "asc" } } },
});

export async function generateMetadata({ params }: Props): Promise<Metadata> {
  const p = await load((await params).slug);
  if (!p) return {};
  return { title: p.seoTitle || p.name, description: p.seoDesc || p.shortDescription || undefined, alternates: { canonical: `/products/${p.slug}` }, openGraph: { images: p.images[0] ? [p.images[0].url] : undefined } };
}

export default async function ProductPage({ params }: Props) {
  const { slug } = await params;
  const p = await load(slug);
  if (!p) notFound();
  const [settings, key] = await Promise.all([getSettings(), ownerKey(false)]);
  const saved = key ? !!(await db.wishlistItem.findUnique({ where: { ownerKey_productId: { ownerKey: key, productId: p.id } } })) : false;

  const variants: VariantView[] = p.variants.map((v) => {
    const av = variantAvailability(v);
    const price = v.price ?? p.basePrice;
    const b = v.batch;
    const st = b ? batchState(b) : null;
    const remaining = b ? remainingCapacity(b) : 0;
    return {
      id: v.id, color: v.color, colorHex: v.colorHex, size: v.size, price, priceLabel: taka(price), mode: v.mode,
      purchasable: av.purchasable, label: av.label, stockQty: v.stockQty,
      maxQty: Math.max(1, Math.min(10, v.mode === "READY_STOCK" ? v.stockQty : remaining)),
      batch: b && st ? {
        state: st, stateLabel: STATE_LABEL[st], remaining, capacity: b.capacity, closes: fmtDate(b.closesAt), opens: fmtDate(b.opensAt),
        dispatch: fmtWindow(b.dispatchFrom, b.dispatchTo), paymentSummary: depositLabel(b),
        depositPerUnit: b.paymentOption === "FULL_ONLY" ? null : depositPerUnit(b, price), depositLabel: depositLabel(b),
        balanceDue: b.paymentOption === "FULL_ONLY" ? null : fmtDate(balanceDueDate(b)), delivery: b.deliveryNote, terms: b.cancellationTerms,
      } : null,
    };
  });

  const related = await db.product.findMany({
    where: { status: "PUBLISHED", id: { in: ((p.relatedIds as string[] | null) ?? []).slice(0, 4) } },
    include: productCardInclude,
  });
  const specs = (p.specs as { label: string; value: string }[] | null) ?? [];
  const price = priceRange({ ...p, variants: p.variants } as never);
  const av = productAvailability({ ...p, variants: p.variants } as never);

  const jsonLd = {
    "@context": "https://schema.org", "@type": "Product", name: p.name, sku: p.sku, description: p.shortDescription ?? p.description,
    image: p.images.slice(0, 4).map((i) => `${process.env.APP_URL ?? ""}${i.url}`), brand: { "@type": "Brand", name: settings.brandName },
    offers: { "@type": "Offer", priceCurrency: "BDT", price: price.min, url: `${process.env.APP_URL ?? ""}/products/${p.slug}`,
      availability: av.purchasable ? (av.mode === "PRE_ORDER" ? "https://schema.org/PreOrder" : "https://schema.org/InStock") : "https://schema.org/OutOfStock" },
  };

  return (
    <>
      <script type="application/ld+json" dangerouslySetInnerHTML={{ __html: JSON.stringify(jsonLd).replace(/</g, "\\u003c") }} />
      <nav aria-label="Breadcrumb" className="wrap py-5 text-[13px] text-stone flex gap-2">
        <Link href="/shop" className="hover:text-ink">Shop all</Link><span aria-hidden>/</span>
        <Link href={`/collections/${p.category.slug}`} className="hover:text-ink">{p.category.name}</Link><span aria-hidden>/</span><span className="text-ink">{p.name}</span>
      </nav>
      <ProductView productId={p.id} name={p.name} shortDescription={p.shortDescription}
        images={p.images.map((i) => ({ id: i.id, url: i.url, alt: i.alt, color: i.color, variantId: i.variantId }))}
        variants={variants} saved={saved} sizeGuide={p.sizeGuide} defaultTerms={settings.preorder.defaultTerms} />

      <section className="wrap grid lg:grid-cols-12 gap-10 py-10 border-t border-sand">
        <div className="lg:col-span-6"><h2 className="font-display text-[32px] mb-4">About this piece</h2><p className="font-display text-[20px] leading-[1.6] max-w-[56ch] whitespace-pre-line">{p.description}</p></div>
        <div className="lg:col-span-5 lg:col-start-8 divide-y divide-sand border-y border-sand self-start">
          <details className="py-4" open><summary className="cursor-pointer nav-type">Details</summary><dl className="mt-3 grid grid-cols-[120px_1fr] gap-y-1.5 text-[14px]">{specs.map((s) => <div key={s.label} className="contents"><dt className="text-stone">{s.label}</dt><dd>{s.value}</dd></div>)}<dt className="text-stone">SKU</dt><dd>{p.sku}</dd></dl></details>
          {p.materials && <details className="py-4"><summary className="cursor-pointer nav-type">Materials</summary><p className="mt-3 text-[14px]">{p.materials}</p></details>}
          {p.care && <details className="py-4"><summary className="cursor-pointer nav-type">Care</summary><p className="mt-3 text-[14px]">{p.care}</p></details>}
          <details className="py-4"><summary className="cursor-pointer nav-type">Delivery and returns</summary><div className="mt-3 text-[14px] space-y-2"><p>Delivery across Bangladesh. Fees are shown at checkout.</p><p><Link className="underline underline-offset-4" href="/shipping-and-returns">Shipping and returns</Link> · <Link className="underline underline-offset-4" href="/pre-order-guide">Pre-order guide</Link></p></div></details>
        </div>
      </section>

      {related.length > 0 && (
        <section className="wrap py-14 border-t border-sand">
          <h2 className="font-display text-[32px] md:text-[44px] mb-8">You may also like</h2>
          <ul className="grid grid-cols-2 lg:grid-cols-4 gap-x-3 md:gap-x-6 gap-y-10">{related.map((r) => <li key={r.id}><ProductCard p={r} /></li>)}</ul>
        </section>
      )}
    </>
  );
}
