import React, { useState, useEffect } from 'react'; import BrowserOnly from '@docusaurus/BrowserOnly'; import { useLocation } from '@docusaurus/router'; import useDocusaurusContext from '@docusaurus/useDocusaurusContext'; import { translate } from '@docusaurus/Translate'; import { useLanguage } from '@site/src/contexts/LanguageContext'; import './ChatbotWidget.css'; const ChatbotWidget = () => { const [isOpen, setIsOpen] = useState(false); const [messages, setMessages] = useState([]); const [inputValue, setInputValue] = useState(''); const [isLoading, setIsLoading] = useState(false); const location = useLocation(); const { siteConfig } = useDocusaurusContext(); const { currentLanguage } = useLanguage(); // Get the current language from context // Function to toggle chatbot window const toggleChatbot = () => { setIsOpen(!isOpen); }; // Function to close chatbot const closeChatbot = () => { setIsOpen(false); }; // Function to handle sending a message const handleSendMessage = async (e) => { e.preventDefault(); if (!inputValue.trim() || isLoading) return; const userMessage = inputValue.trim(); setInputValue(''); // Add user message to chat const newMessages = [...messages, { id: Date.now(), text: userMessage, sender: 'user' }]; setMessages(newMessages); setIsLoading(true); try { // Get JWT token from localStorage const token = localStorage.getItem('token'); if (!token) { // If no token, inform user they need to log in const errorMsg = translate({ id: 'chatbot.loginRequired', message: 'You need to log in to use the chatbot. Please go to the login page.' }); setMessages(prev => [ ...prev, { id: Date.now() + 1, text: errorMsg, sender: 'system' } ]); setIsLoading(false); return; } // Call the backend API with the current language const response = await fetch('/api/chat/query', { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${token}` }, body: JSON.stringify({ query: userMessage, language: currentLanguage // Use the selected language from context }) }); if (!response.ok) { if (response.status === 401) { // Token might be expired, redirect to login localStorage.removeItem('token'); const errorMsg = translate({ id: 'chatbot.authExpired', message: 'Your session has expired. Please log in again.' }); setMessages(prev => [ ...prev, { id: Date.now() + 1, text: errorMsg, sender: 'system' } ]); } else { throw new Error(`API error: ${response.status}`); } } else { const data = await response.json(); setMessages(prev => [ ...prev, { id: Date.now() + 1, text: data.response, sender: 'bot' } ]); } } catch (error) { console.error('Chatbot error:', error); const errorMsg = translate({ id: 'chatbot.errorMessage', message: 'Sorry, I encountered an error. Please try again.' }); setMessages(prev => [ ...prev, { id: Date.now() + 1, text: errorMsg, sender: 'system' } ]); } finally { setIsLoading(false); } }; // Close chatbot when navigating to auth pages useEffect(() => { if (location.pathname.includes('/login') || location.pathname.includes('/signup')) { setIsOpen(false); } }, [location]); return ( {() => { // Only render if not on auth pages const shouldRender = !location.pathname.includes('/login') && !location.pathname.includes('/signup'); return shouldRender ? ( <> {/* Floating Chatbot Icon */}
🤖
{/* Chatbot Window */} {isOpen && (

{translate({ id: 'chatbot.title', message: 'AI Assistant' })}

{messages.length === 0 ? (
{translate({ id: 'chatbot.welcome', message: 'Hello! I\'m your AI assistant. Ask me anything about the Physical AI & Humanoid Robotics book.' })}
) : ( messages.map((message) => (
{message.text}
)) )} {isLoading && (
)}
setInputValue(e.target.value)} placeholder={translate({ id: 'chatbot.inputPlaceholder', message: 'Ask a question...' })} disabled={isLoading} />
)} ) : null; }}
); }; export default ChatbotWidget;