import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
import { useRef, useEffect } from 'react';
import { useStreamingSSE } from '../../../hooks/useStreamingSSE.js';
import { Message } from '../../core/Message/Message.js';
import { TypeWriter } from '../../core/Message/TypeWriter.js';
import '../../core/Message/MessageBody.js';
import 'clsx';
import 'tailwind-merge';
import '../../core/Button/Button.js';
import '@heroicons/react/16/solid';
import '@heroicons/react/24/outline';
import '@heroicons/react/24/solid';
import { ErrorDisplay } from './ErrorDisplay.js';
import { MarkdownRenderer } from './MarkdownRenderer.js';
import { AnimatedText } from './AnimatedText.js';
import { StreamingCursor } from './StreamingCursor.js';

/**
 * StreamingResponse component for AI/LLM streaming responses
 *
 * @example
 * ```tsx
 * <StreamingResponse
 *   url="/api/chat"
 *   method="POST"
 *   body={{ message: "Hello", model: "gpt-4" }}
 *   format="openai"
 *   animated={true}
 *   showCursor={true}
 *   onComplete={(text) => console.log('Completed:', text)}
 * />
 * ```
 */
const StreamingResponse = ({ 
// SSE Configuration
url, method = 'POST', headers, body, format = 'openai', autoStart = true, 
// Callbacks
onToken, onComplete, onError, onStart, onAbort, 
// Display options
typingSpeed = 100, enableTypewriter = true, enableMarkdown = true, markdownOptions, 
// Animation
animated = true, showCursor = true, animateLastN = 12, 
// Message component props
role = 'assistant', avatar, showTimestamp = true, showActions = true, onCopy, onRegenerate, 
// Error handling
retry, timeout = 30000, showError = true, renderError, 
// Styling
className, }) => {
    const startTimeRef = useRef(new Date());
    useEffect(() => { startTimeRef.current = new Date(); }, [url]);
    // Use streaming SSE hook
    const { accumulatedText, isStreaming, error, isComplete, retryAttempt, retry: retryStreaming, } = useStreamingSSE({
        url,
        method,
        headers,
        body,
        format,
        autoStart,
        timeout,
        retry,
        onToken,
        onComplete,
        onError,
        onStart,
        onAbort,
    });
    // Determine content to display
    let messageContent;
    if (error && showError) {
        // Show error display
        messageContent = renderError ? (renderError(error, retryStreaming)) : (jsx(ErrorDisplay, { error: error, onRetry: retryStreaming, retryAttempt: retryAttempt, maxAttempts: (retry === null || retry === void 0 ? void 0 : retry.maxAttempts) || 3 }));
    }
    else if (enableMarkdown) {
        // Render markdown with block-level slide-in animations and streaming cursor
        messageContent = (jsx(MarkdownRenderer, { content: accumulatedText, options: markdownOptions, isStreaming: isStreaming, animated: animated, showCursor: showCursor, animateLastN: animateLastN }));
    }
    else if (isStreaming) {
        // During streaming without markdown: use per-token fade-in animation
        messageContent = (jsxs(Fragment, { children: [jsx(AnimatedText, { text: accumulatedText, isStreaming: isStreaming, enabled: animated }), jsx(StreamingCursor, { visible: showCursor, enabled: animated })] }));
    }
    else if (enableTypewriter && isComplete && accumulatedText) {
        // Use typewriter animation after streaming completes
        messageContent = (jsx(TypeWriter, { text: accumulatedText, speed: typingSpeed, enabled: true, className: "whitespace-pre-wrap wrap-break-word" }));
    }
    else {
        // Show raw text (streaming complete, typewriter disabled)
        messageContent = (jsx("p", { className: "whitespace-pre-wrap wrap-break-word", children: accumulatedText }));
    }
    // Render with Message component
    return (jsx(Message, { role: role, content: messageContent, avatar: avatar, timestamp: startTimeRef.current, showTimestamp: showTimestamp, isStreaming: isStreaming, showActions: showActions && !error, onCopy: onCopy, onRegenerate: onRegenerate, className: className }));
};
StreamingResponse.displayName = 'StreamingResponse';

export { StreamingResponse };
