import { chatAPI } from '@/lib/api';
import { useAuthStore } from '@/stores/authStore';
import { useChatStore } from '@/stores/chatStore';
import { useSocketStore } from '@/stores/socketStore';
import type { Message } from '@/types';
import { useQuery } from '@tanstack/react-query';
import { useEffect, useRef, useState, type FC } from 'react';
import { MessageCard } from './MessageCard';
import { TypingIndicator } from './TypingIndicator';
import { ScrollArea } from './ui/scroll-area';

type MessageListProps = {
  roomId: string;
};

export const MessageList: FC<MessageListProps> = ({ roomId }) => {
  const { messages, setMessages, removeMessage } = useChatStore();
  const { socket } = useSocketStore();
  const { user } = useAuthStore();
  const [lastMessageId, setLastMessageId] = useState<string | null>(null);

  const messagesEndRef = useRef<HTMLDivElement>(null);
  const scrollAreaRef = useRef<HTMLDivElement>(null);
  const roomMessages = messages[roomId] ?? [];

  const { isLoading } = useQuery({
    queryKey: ['messages', roomId],
    queryFn: async () => {
      const response = await chatAPI.getMessages(roomId);
      if (response.data.success) {
        setMessages(roomId, response.data.data);
        return response.data.data;
      }
      throw new Error(response.data.error ?? 'Failed to fetch messages');
    },
    enabled: !!roomId,
  });

  useEffect(() => {
    if (!isLoading && roomMessages.length > 0) {
      setTimeout(() => {
        messagesEndRef.current?.scrollIntoView({ behavior: 'auto' });
      }, 100);
    }
  }, [isLoading, roomId]);

  useEffect(() => {
    if (roomMessages.length > 0) {
      const currentLastMessageId = roomMessages[roomMessages.length - 1].id;

      if (currentLastMessageId !== lastMessageId) {
        setLastMessageId(currentLastMessageId);

        setTimeout(() => {
          messagesEndRef.current?.scrollIntoView({ behavior: 'smooth' });
        }, 50);
      }
    }
  }, [roomMessages, lastMessageId]);

  useEffect(() => {
    const handleImageLoad = () => {
      messagesEndRef.current?.scrollIntoView({ behavior: 'smooth' });
    };

    const container = scrollAreaRef.current;
    if (container) {
      const images = container.querySelectorAll('img');
      images.forEach((img) => {
        if (!img.complete) {
          img.addEventListener('load', handleImageLoad);
        }
      });

      return () => {
        const images = container.querySelectorAll('img');
        images.forEach((img) => {
          img.removeEventListener('load', handleImageLoad);
        });
      };
    }
  }, [roomMessages]);

  useEffect(() => {
    if (!socket || !user || !roomId || roomMessages.length === 0) return;

    const unseenMessages = roomMessages.filter(
      (msg) => msg.userId !== user.id && !msg.seenBy?.includes(user.id)
    );

    if (unseenMessages.length > 0) {
      socket.emit('messages_seen', {
        roomId,
        messageIds: unseenMessages.map((msg) => msg.id),
      });
    }
  }, [socket, user, roomId, roomMessages]);

  useEffect(() => {
    if (!socket) return;

    const handleMessageDeleted = (data: {
      messageId: string;
      roomId: string;
    }) => {
      if (data.roomId === roomId) {
        removeMessage(data.messageId, data.roomId);
      }
    };

    socket.on('message_deleted', handleMessageDeleted);

    return () => {
      socket.off('message_deleted', handleMessageDeleted);
    };
  }, [socket, roomId, removeMessage]);

  if (isLoading) {
    return (
      <div className="flex-1 flex items-center justify-center dark:bg-gray-900">
        <div className="h-8 w-8 rounded-full border-4 border-gray-300 border-t-gray-500 animate-spin dark:border-gray-600 dark:border-t-gray-300"></div>
      </div>
    );
  }

  return (
    <div className="flex-1 overflow-hidden bg-white dark:bg-gray-900">
      <ScrollArea className="h-full" ref={scrollAreaRef}>
        <div className="space-y-4 p-4">
          {roomMessages.map((message: Message) => (
            <MessageCard key={message.id} message={message} />
          ))}
          <div ref={messagesEndRef} />
          <TypingIndicator roomId={roomId} />
        </div>
      </ScrollArea>
    </div>
  );
};
