import { createRef, useEffect, useRef, useState } from 'react';
import classNames from 'classnames';
import { v4 } from 'uuid';

import styles from './index.module.scss';
import { PremiumSettings, Settings } from '../../types/types';
import MessageBox from './MessageBox';

interface ChatBotWindowProps {
  settings: Settings;
  premiumSettings: PremiumSettings;
  show?: boolean;
  setShow?: Function;
  customizeMode?: boolean;
}
export default function ChatBotWindow({
  settings,
  premiumSettings,
  show,
  setShow,
  customizeMode,
}: ChatBotWindowProps) {
  const [hover, setHover] = useState(false);
  const [message, setMessage] = useState('');
  const [error, setError] = useState('');
  const sessionId = useRef(v4());
  const [chatLog, setChatLog] = useState([
    {
      user: 'bot',
      message: settings.chatBotOpeningMsg,
    },
  ]);
  const [thinking, setThinking] = useState(false);
  const chatbotBodyRef = createRef<HTMLDivElement>();

  useEffect(() => {
    const chatbotBody = chatbotBodyRef.current;
    if (!chatbotBody) return;
    chatbotBody.scrollTop = chatbotBody.scrollHeight;
  }, [chatbotBodyRef]);

  function _setChatLogBot(log: any) {
    setChatLog((value) => {
      return [...value, log];
    });
  }

  function _setChatLog(log: any) {
    setChatLog((value) => {
      return [...value, log];
    });

    setMessage('');
  }

  /**
   * Send a message to the chatbot
   */
  async function sendMessage() {
    if (!message || thinking) return;
    _setChatLog({
      user: 'user',
      message,
    });

    let messageObject = {
      message: message,
      env: process.env.NODE_ENV,
      session_id: sessionId.current,
    };

    if (premiumSettings.active) {
      messageObject = {
        ...messageObject,
        ...{
          mainGoal: premiumSettings.mainGoal,
          customInstructions: premiumSettings.customInstructions,
          premiumActive: true,
        },
      };
    }
    setThinking(true);
    const request = await fetch(
      `${wpApiSettings.root}botfoundry/v1/send-message`,
      {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
          'X-WP-Nonce': wpApiSettings.nonce,
        },
        body: JSON.stringify(messageObject),
      }
    );

    const data = await request.json();
    setThinking(false);
    if (request.ok && !data?.error) {
      _setChatLogBot({
        user: 'bot',
        message: data,
      });
    } else {
      if (customizeMode && data?.error) {
        setError(data?.error);
      } else {
        setError('An error occurred while sending the message');
      }
    }
  }

  function renderPoweredByLogo() {
    if (premiumSettings.active && premiumSettings.noPoweredBy) {
      return <></>;
    }
    return (
      <div className={styles['chatbot-footer-powered-by']}>
        <p className={styles['chatbot-footer-powered-by-text']}>
          Powered by {process.env.PLUGIN_NAME}
        </p>
      </div>
    );
  }

  if (!show) return null;
  return (
    <div
      className={classNames(
        styles['botfoundry-chatbot-window'],
        customizeMode ? styles['customize-mode'] : null
      )}
    >
      <div
        className={styles['chatbot-header']}
        style={{ backgroundColor: settings.chatBotPrimaryColor }}
      >
        <div className={styles['chatbot-header-title']}>
          <h3>{settings.chatBotTitle}</h3>
        </div>
        <div
          onClick={() => {
            setShow && setShow(false);
          }}
          className={styles['chatbot-header-close']}
        >
          <span>&times;</span>
        </div>
      </div>
      <div className={styles['chatbot-body-wrapper']}>
        <div className={styles['chatbot-body']} ref={chatbotBodyRef}>
          <div className={styles['chatbot-body-inner']}>
            {chatLog.map((log, index) => (
              <MessageBox key={index} user={log.user} settings={settings}>
                {log.message}
              </MessageBox>
            ))}
            {thinking ? (
              <MessageBox user={'bot'} settings={settings}>
                <span className="thinking-dots">
                  Thinking<span className="dots"></span>
                </span>
              </MessageBox>
            ) : null}
            {error && (
              <div className={styles['chatbot-message']}>
                <p className={styles['chatbot-message-content']}>{error}</p>
              </div>
            )}
          </div>
        </div>
      </div>
      <div className={styles['chatbot-footer']}>
        <input
          onChange={(e) => setMessage(e.target.value)}
          type="text"
          placeholder="Type your message here..."
          className={styles['chatbot-footer-input']}
          onKeyDown={(e) => e.key === 'Enter' && sendMessage()}
          value={message}
        />
        <button
          className={classNames(
            styles['chatbot-footer-send'],
            'ease-in-out',
            thinking ? 'disabled' : ''
          )}
          style={{
            backgroundColor: hover
              ? settings.chatBotSecondaryColor
              : settings.chatBotPrimaryColor,
          }}
          onMouseEnter={() => setHover(true)}
          onMouseLeave={() => setHover(false)}
          onClick={sendMessage}
        >
          Send
        </button>
      </div>
      {renderPoweredByLogo()}
    </div>
  );
}
