"use client";

import { useEffect, useRef, useState } from "react";
import { Coupon, DiscountType } from "@prisma/client";
import { useRouter } from "next/navigation";
import { toast } from "react-toastify";

interface CategoryType {
  id: string;
  name: string;
}

interface CollectionType {
  id: string;
  title: string;
}

interface ProductType {
  id: string;
  product_name: string;
}

interface ProductVariant {
  id: string;
  name: string;
}

interface DiscountCouponsFormProps {
  initialData?: CouponsType | null;
}

function translateDiscountType(type: string){
  if (type == "PERCENTAGE") return "Percentage";
  if (type == "FIXED_AMOUNT") return "Fixed";
  if (type == "FREE_SHIPPING") return "FreeShipping";
  
  return type;
}

const DiscountCouponsForm: React.FC<DiscountCouponsFormProps> = ({ initialData }) => {
  const router = useRouter();

  const [loading, setLoading] = useState(false);
  const [code, setCode] = useState(initialData?.code || "");

  const [type, setType] = useState<string>(translateDiscountType(initialData?.type) || "Fixed");
  
  
  const [value, setValue] = useState(initialData?.value || 0);
  const [maxDiscount, setMaxDiscount] = useState<number | null>(initialData?.maxDiscount || null);
  const [minPurchaseAmount, setMinPurchaseAmount] = useState<number | null>(
    initialData?.minPurchaseAmount || null
  );
  const [startDate, setStartDate] = useState(
    initialData?.startDate ? new Date(initialData.startDate).toISOString().split("T")[0] : ""
  );
  const [endDate, setEndDate] = useState(
    initialData?.endDate ? new Date(initialData.endDate).toISOString().split("T")[0] : ""
  );
  const [usageLimit, setUsageLimit] = useState<number | null>(initialData?.usageLimit || null);
  const [perUserLimit, setPerUserLimit] = useState<number | null>(initialData?.perUserLimit || null);
  const [isActive, setIsActive] = useState(initialData?.isActive ?? true);

  const [categories, setCategories] = useState<CategoryType[]>([]);
  const [collections, setCollections] = useState<CollectionType[]>([]);
  const [products, setProducts] = useState<ProductType[]>([]);
  const [variants, setVariants] = useState<ProductVariant[]>([]);

  const [selectedProducts, setSelectedProducts] = useState<string[]>([]);
  const [selectedVariants, setSelectedVariants] = useState<string[]>([]);
  const [selectedCategories, setSelectedCategories] = useState<string[]>([]);
  const [selectedCollections, setSelectedCollections] = useState<string[]>([]);

  const [productHasMore, setProductHasMore] = useState(false);
  const [productPage, setProductPage] = useState(1);
  const [productsTotal, setProductsTotal] = useState(0);
  const [productLimit, setProductLimit] = useState(10);
  const [loadingProducts, setLoadingProducts] = useState(false);

  const [variantHasMore, setVariantHasMore] = useState(false);
  const [variantPage, setVariantPage] = useState(1);
  const [variantsTotal, setVariantsTotal] = useState(0);
  const [variantLimit, setVariantLimit] = useState(10);
  const [loadingVariants, setLoadingVariants] = useState(false);

  const productsDivRef = useRef<HTMLDivElement>(null);
  const variantsDivRef = useRef<HTMLDivElement>(null);

  const fetchCategories = async () => {
    const res = await fetch("/api/admin/categories", { cache: "no-store" });
    const data = await res.json();
    setCategories(data.data);

    if (initialData?.categories) {
      setSelectedCategories(initialData.categories.map((cat: any) => String(cat.id)));
    }
  };

  const fetchCollections = async () => {
    const res = await fetch("/api/admin/collections", { cache: "no-store" });
    const data = await res.json();
    setCollections(data.data);

    if (initialData?.collections) {
      setSelectedCollections(initialData.collections.map((col: any) => String(col.id)));
    }

  };

  const fetchProducts = async (page = 1) => {
    setLoadingProducts(true);
    try {
      const res = await fetch(`/api/admin/products?page=${page}&limit=${productLimit}`, {
        cache: "no-store",
      });
      const data = await res.json();

      if (page === 1) {
        setProducts(data.products);
      } else {
        setProducts((prev) => [...prev, ...data.products]);
      }

      setProductsTotal(data.total);
      setProductHasMore(data.products.length + (page - 1) * productLimit < data.total);

      if (initialData?.products) {
        setSelectedProducts(initialData.products.map((prod: any) => String(prod.id)));
      }

    } catch (err) {
      console.error("Error fetching products:", err);
    } finally {
      setLoadingProducts(false);
    }
  };

  const fetchVariants = async (page = 1) => {
    setLoadingVariants(true);
    try {
      const res = await fetch(`/api/admin/variants?page=${page}&limit=${variantLimit}`, {
        cache: "no-store",
      });
      const data = await res.json();

      if (page === 1) {
        setVariants(data.variants);
      } else {
        setVariants((prev) => [...prev, ...data.variants]);
      }

      setVariantsTotal(data.total);
      setVariantHasMore(data.variants.length + (page - 1) * variantLimit < data.total);


      if (initialData?.variants) {
        setSelectedVariants(initialData.variants.map((variant: any) => String(variant.id)));
      }

    } catch (err) {
      console.error("Error fetching variants:", err);
    } finally {
      setLoadingVariants(false);
    }
  };


  const handleProductSelect = (e: React.ChangeEvent<HTMLSelectElement>) => {
    const selected = Array.from(e.target.selectedOptions, (option) => option.value);
    setSelectedProducts(selected);
  };

  const handleVariantSelect = (e: React.ChangeEvent<HTMLSelectElement>) => {
    const selected = Array.from(e.target.selectedOptions, (option) => option.value);
    setSelectedVariants(selected);
  };

  const handleCategorySelect = (e: React.ChangeEvent<HTMLSelectElement>) => {
    setSelectedCategories(Array.from(e.target.selectedOptions, (option) => option.value));
  };

  const handleCollectionSelect = (e: React.ChangeEvent<HTMLSelectElement>) => {
    setSelectedCollections(Array.from(e.target.selectedOptions, (option) => option.value));
  };


  useEffect(() => {
    fetchCategories();
    fetchCollections();
    fetchProducts(1);
    fetchVariants(1);
  }, []);

  const onSubmit = async (e: React.FormEvent) => {
    e.preventDefault();
    try {
      setLoading(true);

      const formData = new FormData();
      formData.append("code", code);
      formData.append("type", type);
      formData.append("value", value.toString());
      formData.append("maxDiscount", maxDiscount?.toString() || "");
      formData.append("minPurchaseAmount", minPurchaseAmount?.toString() || "");
      formData.append("startDate", startDate ? new Date(startDate).toISOString() : "");
      formData.append("endDate", endDate ? new Date(endDate).toISOString() : "");
      formData.append("usageLimit", usageLimit?.toString() || "");
      formData.append("perUserLimit", perUserLimit?.toString() || "");
      formData.append("isActive", isActive ? "true" : "false");

      formData.append("selectedProducts", JSON.stringify(selectedProducts));
      formData.append("selectedVariants", JSON.stringify(selectedVariants));
      formData.append("selectedCategories", JSON.stringify(selectedCategories));
      formData.append("selectedCollections", JSON.stringify(selectedCollections));


      const method = initialData ? "PUT" : "POST";
      const url = initialData
        ? `/api/admin/coupons/${initialData.id}`
        : `/api/admin/coupons`;

      const response = await fetch(url, { method, body: formData });

      if (!response.ok) throw new Error("Failed to save coupon");

      router.push("/admin/coupons");
      toast.success(`Coupon ${initialData ? "updated" : "created"} successfully!`);
    } catch (err) {
      console.error("Error saving coupon:", err);
      alert("Error saving coupon. Please check console for details.");
    } finally {
      setLoading(false);
    }
  };

  return (
    <div className="p-8 max-w-4xl mx-auto border rounded-md shadow-md bg-white">
      <h2 className="text-2xl font-bold mb-6">
        {initialData ? "Edit Coupon" : "Create New Coupon"}
      </h2>

      <form className="space-y-6" onSubmit={onSubmit}>
        {/* Coupon Code */}
        <div>
          <label className="block text-sm font-medium mb-1">Coupon Code</label>
          <input
            type="text"
            value={code}
            onChange={(e) => setCode(e.target.value)}
            className="w-full border rounded-md p-2"
            placeholder="e.g. SAVE10"
          />
        </div>

        {/* Type */}
        <div>
          <label className="block text-sm font-medium mb-1">Discount Type</label>
          <select
            value={type}
            onChange={(e) => setType(e.target.value as DiscountType)}
            className="w-full border rounded-md p-2"
          >
            <option value="Fixed">Fixed</option>
            <option value="Percentage">Percentage</option>
            <option value="FreeShipping">Free Shipping</option>
          </select>
        </div>

        {/* Value */}
        <div>
          <label className="block text-sm font-medium mb-1">Value</label>
          <input
            type="number"
            step="0.01"
            value={value}
            onChange={(e) => setValue(Number(e.target.value))}
            className="w-full border rounded-md p-2"
            placeholder="Discount amount or percentage"
          />
        </div>

        {/* Max Discount */}
        <div>
          <label className="block text-sm font-medium mb-1">Max Discount (optional)</label>
          <input
            type="number"
            step="0.01"
            value={maxDiscount ?? ""}
            onChange={(e) =>
              setMaxDiscount(e.target.value ? Number(e.target.value) : null)
            }
            className="w-full border rounded-md p-2"
            placeholder="Maximum discount value"
          />
        </div>

        {/* Min Purchase */}
        <div>
          <label className="block text-sm font-medium mb-1">
            Minimum Purchase Amount (optional)
          </label>
          <input
            type="number"
            step="0.01"
            value={minPurchaseAmount ?? ""}
            onChange={(e) =>
              setMinPurchaseAmount(e.target.value ? Number(e.target.value) : null)
            }
            className="w-full border rounded-md p-2"
            placeholder="Minimum cart value to apply coupon"
          />
        </div>

        {/* Dates */}
        <div className="grid grid-cols-1 sm:grid-cols-2 gap-4">
          <div>
            <label className="block text-sm font-medium mb-1">Start Date</label>
            <input
              type="date"
              value={startDate}
              onChange={(e) => setStartDate(e.target.value)}
              className="w-full border rounded-md p-2"
            />
          </div>

          <div>
            <label className="block text-sm font-medium mb-1">End Date</label>
            <input
              type="date"
              value={endDate}
              onChange={(e) => setEndDate(e.target.value)}
              className="w-full border rounded-md p-2"
            />
          </div>
        </div>

        {/* Usage Limit */}
        <div>
          <label className="block text-sm font-medium mb-1">Usage Limit</label>
          <input
            type="number"
            value={usageLimit ?? ""}
            onChange={(e) =>
              setUsageLimit(e.target.value ? Number(e.target.value) : null)
            }
            className="w-full border rounded-md p-2"
            placeholder="Total times coupon can be used"
          />
        </div>

        {/* Per User Limit */}
        <div>
          <label className="block text-sm font-medium mb-1">Per User Limit</label>
          <input
            type="number"
            value={perUserLimit ?? ""}
            onChange={(e) =>
              setPerUserLimit(e.target.value ? Number(e.target.value) : null)
            }
            className="w-full border rounded-md p-2"
            placeholder="Times a single user can use coupon"
          />
        </div>

        {/* Categories */}
        <div>
          <label className="block text-sm font-medium mb-1">Select Categories</label>
          <select
            multiple
            value={selectedCategories}
            onChange={handleCategorySelect}
            className="w-full border rounded-md p-2 h-40"
          >
            {categories.map((cat) => (
              <option key={cat.id} value={cat.id}>
                {cat.name}
              </option>
            ))}
          </select>
        </div>

        {/* Collections */}
        <div>
          <label className="block text-sm font-medium mb-1">Select Collections</label>
          <select
            multiple
            value={selectedCollections}
            onChange={handleCollectionSelect}
            className="w-full border rounded-md p-2 h-40"
          >
            {collections.map((col) => (
              <option key={col.id} value={col.id}>
                {col.title}
              </option>
            ))}
          </select>
        </div>

        {/* Products */}
        <div ref={productsDivRef}>
          <label className="block text-sm font-medium mb-1">Select Products</label>
          <select
            multiple
            value={selectedProducts}
            onChange={handleProductSelect}
            className="w-full border rounded-md p-2 h-40"
          >
            {products.map((product) => (
              <option key={product.id} value={product.id}>
                {product.product_name}
              </option>
            ))}
          </select>

          <div className="flex justify-center mt-2">
            {loadingProducts && <p className="text-gray-500 text-sm">Loading...</p>}
            {!loadingProducts && productHasMore && (
              <button
                type="button"
                onClick={() => {
                  const nextPage = productPage + 1;
                  setProductPage(nextPage);
                  fetchProducts(nextPage);
                }}
                className="text-blue-600 text-sm hover:underline"
              >
                Load More Products
              </button>
            )}
            {!productHasMore && !loadingProducts && products.length > 0 && (
              <p className="text-gray-400 text-xs">All products loaded</p>
            )}
          </div>
        </div>

        {/* Variants */}
        <div ref={variantsDivRef}>
          <label className="block text-sm font-medium mb-1">Select Variants</label>
          <select
            multiple
            value={selectedVariants}
            onChange={handleVariantSelect}
            className="w-full border rounded-md p-2 h-40"
          >
            {variants.map((variant) => (
              <option key={variant.id} value={variant.id}>
                {variant.name}
              </option>
            ))}
          </select>

          <div className="flex justify-center mt-2">
            {loadingVariants && <p className="text-gray-500 text-sm">Loading...</p>}
            {!loadingVariants && variantHasMore && (
              <button
                type="button"
                onClick={() => {
                  const nextPage = variantPage + 1;
                  setVariantPage(nextPage);
                  fetchVariants(nextPage);
                }}
                className="text-blue-600 text-sm hover:underline"
              >
                Load More Variants
              </button>
            )}
            {!variantHasMore && !loadingVariants && variants.length > 0 && (
              <p className="text-gray-400 text-xs">All variants loaded</p>
            )}
          </div>
        </div>

        {/* Status */}
        <div className="flex items-center gap-2">
          <input
            type="checkbox"
            checked={isActive}
            onChange={(e) => setIsActive(e.target.checked)}
          />
          <label className="text-sm font-medium">Active</label>
        </div>

        {/* Submit */}
        <div className="flex gap-4">
          <button
            type="submit"
            disabled={loading}
            className="bg-blue-600 text-white px-6 py-2 rounded-md hover:bg-blue-700 disabled:opacity-50"
          >
            {loading ? "Saving..." : initialData ? "Update Coupon" : "Create Coupon"}
          </button>

          {!initialData && (
            <button
              type="button"
              onClick={() => {
                setCode("");
                setValue(0);
                setMaxDiscount(null);
                setMinPurchaseAmount(null);
                setStartDate("");
                setEndDate("");
                setUsageLimit(null);
                setPerUserLimit(null);
                setIsActive(true);
              }}
              className="bg-gray-300 text-black px-6 py-2 rounded-md hover:bg-gray-400"
            >
              Discard
            </button>
          )}
        </div>
      </form>
    </div>
  );
};

export default DiscountCouponsForm;
