import type { FC } from 'react';
import React, { useEffect, useRef } from 'react';
import cx from 'classnames';
import { Toast } from './toast';
import type { Message } from './types';
import { ANIMATION_TIME } from './types';

const CLASS_NAME = 'ToastContainer';

export interface ToastContainerProps {
    className?: string;
    messages: Message[];
    setMessages?: (messages: Message[]) => void;
    removeToast?: (id: string) => void;
    testId?: string;
    toastTime: number;
}

export const ToastContainer: FC<ToastContainerProps> = ({
    className,
    messages,
    setMessages,
    removeToast,
    testId = CLASS_NAME,
    toastTime,
}) => {
    const timerRef = React.useRef<number>();
    const containerRef = useRef<HTMLDivElement>(null);
    const hasMessages = messages.length > 0;

    useEffect(() => {
        if (timerRef.current) window.clearTimeout(timerRef.current);

        // Only auto-clear non-persistent toasts
        const nonPersistentMessages = messages.filter((msg) => !msg.persistent);

        if (nonPersistentMessages.length > 0) {
            timerRef.current = window.setTimeout(() => {
                const persistentMessages = messages.filter((msg) => msg.persistent);
                setMessages?.(persistentMessages);
            }, toastTime + ANIMATION_TIME);
        }
    }, [messages, setMessages, toastTime]);

    useEffect(() => {
        const node = containerRef.current;
        if (!node || typeof node.showPopover !== 'function') return;
        if (!node.matches(':popover-open')) node.showPopover();
    }, [hasMessages]);

    if (!hasMessages) return null;

    return (
        <div
            ref={containerRef}
            // @ts-expect-error popover is not yet in the types
            // eslint-disable-next-line react/no-unknown-property
            popover="manual"
            className={cx(CLASS_NAME, className)}
            data-testid={testId}
        >
            {messages.map((message) => (
                <Toast
                    key={message.id}
                    message={message}
                    toastTime={toastTime}
                    onClose={removeToast}
                />
            ))}
        </div>
    );
};
