import { useState, useCallback, useRef, useEffect } from 'react';
import AsyncSelect from 'react-select/async';
import Image from 'next/image';
import { coloredToast } from '@/lib/toast';

interface Product {
    id?: string;
    _id?: string;
    product_title: string;
}

interface SelectOption {
    value: string;
    label: string;
}

const normalizeImagesFromApi = (image?: string | string[]): string[] => {
    if (!image) return [''];
    if (Array.isArray(image)) {
        return image.length > 0 ? image : [''];
    }
    const trimmed = image.trim();
    if (!trimmed) return [''];
    return [trimmed];
};

export default function HighlightProduct() {
    const [selectedProducts, setSelectedProducts] = useState<SelectOption[]>([]);
    const [images, setImages] = useState<string[]>(['']);
    const [isLoading, setIsLoading] = useState(false);
    const [isLoadingData, setIsLoadingData] = useState(true);
    const debounceTimeoutRef = useRef<NodeJS.Timeout | null>(null);
    const [status, setStatus] = useState(false);

    const fetchData = useCallback(async (inputValue: string): Promise<SelectOption[]> => {
        try {
            const api_url = process.env.API_URL;
            const response = await fetch(`${api_url}api/products/product-list?q=${inputValue}`, {
                method: 'GET',
                headers: { 'Content-Type': 'application/json' },
                credentials: 'include',
            });

            if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);

            const data = await response.json();
            const products = Array.isArray(data) ? data : data.data || [];

            return products.map((item: Product) => ({
                value: String(item._id ?? item.id ?? ''),
                label: item.product_title ?? '',
            }));
        } catch (error) {
            console.error('Error fetching data:', error);
            return [];
        }
    }, []);

    const loadOptions = useCallback(
        (inputValue: string): Promise<SelectOption[]> => {
            return new Promise((resolve) => {
                if (debounceTimeoutRef.current) clearTimeout(debounceTimeoutRef.current);

                if (inputValue.length >= 3) {
                    debounceTimeoutRef.current = setTimeout(async () => {
                        try {
                            setIsLoading(true);
                            const options = await fetchData(inputValue);
                            resolve(options);
                        } catch (error) {
                            console.error('Error loading options:', error);
                            resolve([]);
                        } finally {
                            setIsLoading(false);
                        }
                    }, 300);
                } else {
                    resolve([]);
                }
            });
        },
        [fetchData]
    );

    const handleImageChange = (index: number, value: string) => {
        setImages((prevImages) =>
            prevImages.map((image, imageIndex) =>
                imageIndex === index ? value : image
            )
        );
    };

    const handleAddImage = () => {
        setImages((prevImages) => [...prevImages, '']);
    };

    const handleRemoveImage = (index: number) => {
        setImages((prevImages) => {
            const nextImages = prevImages.filter((_, imageIndex) => imageIndex !== index);
            return nextImages.length > 0 ? nextImages : [''];
        });
    };

    const handleSave = useCallback(async () => {
        if (!selectedProducts.length) {
            coloredToast('error', 'Harap pilih minimal satu produk');
            return;
        }

        const payloadImages = images.map((image) => image.trim()).filter(Boolean);

        try {
            setIsLoading(true);
            const api_url = process.env.API_URL;
            const res = await fetch(`${api_url}api/products/highlight-product`, {
                method: 'POST',
                headers: { 'Content-Type': 'application/json' },
                credentials: 'include',
                body: JSON.stringify({
                    products: selectedProducts,
                    images: payloadImages,
                }),
            });

            if (!res.ok) throw new Error(`HTTP error! status: ${res.status}`);

            const data = await res.json();
            if (data.success) {
                setSelectedProducts(data.data.products || []);
                setImages(normalizeImagesFromApi(data.data.images ?? data.data.image));
                coloredToast('success', 'Data berhasil disimpan');
            }
        } catch (error) {
            console.error('Error saving highlight product:', error);
            coloredToast('error', 'Gagal menyimpan data');
        } finally {
            setIsLoading(false);
        }
    }, [selectedProducts, images]);

    const loadHighlightedProducts = useCallback(async () => {
        try {
            setIsLoadingData(true);
            const api_url = process.env.API_URL;
            const response = await fetch(`${api_url}api/products/highlight-product`, {
                method: 'GET',
                headers: { 'Content-Type': 'application/json' },
                credentials: 'include',
            });

            if (response.ok) {
                const data = await response.json();
                if (data.success) {
                    setSelectedProducts(data.data.products || []);
                    setImages(normalizeImagesFromApi(data.data.images ?? data.data.image));
                }
            }
        } catch (error) {
            console.error('Error loading highlighted products:', error);
        } finally {
            setIsLoadingData(false);
        }
    }, []);

    useEffect(() => {
        loadHighlightedProducts();
    }, [loadHighlightedProducts]);

    useEffect(() => {
        const getStatus = async () => {
            const api_url = process.env.API_URL;
            const response = await fetch(`${api_url}api/setting/highlight-status`, {
                method: 'GET',
            });
            const statusData = await response.json();
            setStatus(statusData.status || false);
        };
        getStatus();
    }, []);

    const handleStatusChange = async () => {
        try {
            const api_url = process.env.API_URL;
            const newStatus = !status;

            const response = await fetch(`${api_url}api/setting/highlight-status`, {
                method: 'PUT',
                headers: {
                    'Content-Type': 'application/json',
                },
                credentials: 'include',
                body: JSON.stringify({
                    status: newStatus,
                }),
            });

            if (response.ok) {
                setStatus(newStatus);
            } else {
                console.error('Gagal mengubah status');
            }
        } catch (error) {
            console.error('Error mengubah status:', error);
        }
    };

    return (
        <div className="w-1/2">
            <div className="panel">
                <div className="panel-header">
                    <h1 className="text-xl ">Highlight Product</h1>
                </div>
                <div className="panel-content">
                    <div className="mt-12 flex flex-row gap-8">
                        <div className="w-1/2">
                            <p>Highlight Product</p>
                            <div className="mt-4">
                                {isLoadingData ? (
                                    <div className="flex items-center justify-center p-4">
                                        <div className="text-gray-500">Loading highlighted products...</div>
                                    </div>
                                ) : (
                                    <div className="custom-select">
                                    <AsyncSelect<SelectOption, true>
                                        isMulti
                                        loadOptions={loadOptions}
                                        className="w-full"
                                        placeholder="Ketik minimal 3 karakter"
                                        value={selectedProducts}
                                        onChange={(selectedItems) => {
                                            setSelectedProducts(selectedItems ? [...selectedItems] : []);
                                        }}
                                        noOptionsMessage={() => 'Tidak ada produk ditemukan'}
                                        loadingMessage={() => 'Mencari produk...'}
                                        isClearable
                                        isSearchable
                                        cacheOptions={false}
                                        isLoading={isLoading}
                                        menuPlacement="auto"
                                    />
                                    </div>
                                )}
                            </div>
                        </div>
                        <div className="w-1/2">
                            <div className="flex flex-col">
                                <div>
                                    <p>
                                        Images <span className="text-sm text-gray-500">(Opsional)</span>
                                    </p>
                                    <div className="mt-4 space-y-3">
                                        {images.map((image, index) => (
                                            <div key={index} className="flex items-start gap-2">
                                                <div className="flex-1">
                                                    <input
                                                        type="text"
                                                        className="form-input w-full"
                                                        placeholder={`URL gambar ${index + 1} (opsional)`}
                                                        value={image}
                                                        onChange={(e) => handleImageChange(index, e.target.value)}
                                                    />
                                                    {image.trim() && (
                                                        <div className="mt-2">
                                                            <Image
                                                                src={image.trim()}
                                                                alt={`Preview ${index + 1}`}
                                                                width={80}
                                                                height={80}
                                                                className="rounded object-cover"
                                                            />
                                                        </div>
                                                    )}
                                                </div>
                                                {images.length > 1 && (
                                                    <button
                                                        type="button"
                                                        className="btn btn-outline-danger btn-sm mt-1"
                                                        onClick={() => handleRemoveImage(index)}
                                                    >
                                                        Hapus
                                                    </button>
                                                )}
                                            </div>
                                        ))}
                                        <button
                                            type="button"
                                            className="btn btn-outline-primary btn-sm"
                                            onClick={handleAddImage}
                                        >
                                            Tambah Gambar
                                        </button>
                                    </div>
                                </div>
                                <div className="mt-8">
                                    <label className=" inline-flex cursor-pointer items-center">
                                        <input type="checkbox" value="" className="peer sr-only" checked={status} onChange={handleStatusChange} />
                                        <div className="peer relative h-6 w-11 rounded-full bg-gray-200 after:absolute after:start-[2px] after:top-[2px] after:h-5 after:w-5 after:rounded-full after:border after:border-gray-300 after:bg-white after:transition-all after:content-[''] peer-checked:bg-blue-600 peer-checked:after:translate-x-full peer-checked:after:border-white peer-focus:outline-none peer-focus:ring-4 peer-focus:ring-blue-300 dark:border-gray-600 dark:bg-gray-700 dark:peer-checked:bg-blue-600 dark:peer-focus:ring-blue-800 rtl:peer-checked:after:-translate-x-full"></div>
                                        <span className="ms-3 text-sm font-medium text-gray-900 dark:text-gray-300">Active</span>
                                    </label>
                                </div>
                            </div>
                        </div>
                    </div>
                    <div className="mt-8">
                        <button className="btn btn-primary" onClick={handleSave} disabled={isLoading || isLoadingData}>
                            {isLoading ? 'Saving...' : 'Save'}
                        </button>
                    </div>
                </div>
            </div>
        </div>
    );
}
