import { useState, useRef, useEffect } from "react";
import {
  postV2UploadSubmissionMedia,
  postV2GenerateSubmissionImage,
} from "@/app/api/__generated__/endpoints/store/store";
import { resolveResponse } from "@/app/api/helpers";
import { useToast } from "@/components/molecules/Toast/use-toast";

interface UseThumbnailImagesProps {
  agentId: string | null;
  onImagesChange: (images: string[]) => void;
  initialImages?: string[];
  initialSelectedImage?: string | null;
}

export function useThumbnailImages({
  agentId,
  onImagesChange,
  initialImages = [],
  initialSelectedImage = null,
}: UseThumbnailImagesProps) {
  const [images, setImages] = useState<string[]>(initialImages);

  const [selectedImage, setSelectedImage] = useState<string | null>(
    initialSelectedImage,
  );

  const [isGenerating, setIsGenerating] = useState(false);
  const [isUploading, setIsUploading] = useState(false);
  const thumbnailsContainerRef = useRef<HTMLDivElement | null>(null);
  const { toast } = useToast();

  const initialImagesKey = JSON.stringify(initialImages);

  useEffect(() => {
    if (initialImages.length === 0) {
      setImages([]);
      setSelectedImage(null);
      return;
    }

    const nextSelectedImage = initialSelectedImage || initialImages[0];
    setImages([
      nextSelectedImage,
      ...initialImages.filter((image) => image !== nextSelectedImage),
    ]);
    setSelectedImage(nextSelectedImage);
  }, [initialImagesKey, initialSelectedImage]);

  useEffect(() => {
    onImagesChange(images);
  }, [images, onImagesChange]);

  const setImagesWithValidation = (newImages: string[]) => {
    const uniqueImages = Array.from(new Set(newImages));
    const limitedImages = uniqueImages.slice(0, 5);
    setImages(limitedImages);
  };

  function handleRemoveImage(indexToRemove: number) {
    const removedImage = images[indexToRemove];
    const newImages = [...images];
    newImages.splice(indexToRemove, 1);
    setImagesWithValidation(newImages);
    if (removedImage === selectedImage) {
      setSelectedImage(newImages[0] || null);
    }
    if (newImages.length === 0) {
      setSelectedImage(null);
    }
  }

  async function handleAddImage() {
    if (images.length >= 5) return;

    const input = document.createElement("input");
    input.type = "file";
    input.accept = "image/*";

    const fileSelected = new Promise<File | null>((resolve) => {
      input.onchange = (e) => {
        const file = (e.target as HTMLInputElement).files?.[0];
        resolve(file || null);
      };
    });

    input.click();

    const file = await fileSelected;
    if (!file) return;

    await uploadImage(file);
  }

  async function handleFileChange(e: React.ChangeEvent<HTMLInputElement>) {
    if (images.length >= 5) return;

    const file = e.target.files?.[0];
    if (!file) return;

    await uploadImage(file);
  }

  async function uploadImage(file: File) {
    setIsUploading(true);
    try {
      const mediaRes = await resolveResponse(
        postV2UploadSubmissionMedia({ file }),
      );
      const imageUrl = mediaRes.replace(/^"(.*)"$/, "$1");

      setImagesWithValidation([...images, imageUrl]);
      if (!selectedImage) {
        setSelectedImage(imageUrl);
      }
    } catch (error) {
      const detail =
        error instanceof Error ? error.message : "Please try again.";
      toast({
        title: "Upload failed",
        description: detail,
        variant: "destructive",
      });
    } finally {
      setIsUploading(false);
    }
  }

  async function handleGenerateImage() {
    if (isGenerating || images.length >= 5) return;

    setIsGenerating(true);
    try {
      if (!agentId) {
        throw new Error("Agent ID is required");
      }
      const { image_url } = await resolveResponse(
        postV2GenerateSubmissionImage({ graph_id: agentId }),
      );
      setImagesWithValidation([...images, image_url]);
      if (!selectedImage) {
        setSelectedImage(image_url);
      }
    } catch (_error) {
      toast({
        title: "Generation failed",
        description: "Failed to generate image. Please try again.",
        variant: "destructive",
      });
    } finally {
      setIsGenerating(false);
    }
  }

  function handleImageSelect(imageSrc: string) {
    setSelectedImage(imageSrc);
    setImagesWithValidation([
      imageSrc,
      ...images.filter((src) => src !== imageSrc),
    ]);
  }

  return {
    images,
    selectedImage,
    isGenerating,
    isUploading,
    thumbnailsContainerRef,
    handleRemoveImage,
    handleAddImage,
    handleFileChange,
    handleGenerateImage,
    handleImageSelect,
  };
}
