// CSS imports import '../css/chat-client.css'; import '../../../eveai_chat_client/static/assets/css/chat.css'; import '../../../eveai_chat_client/static/assets/css/chat-components.css'; import '../../../eveai_chat_client/static/assets/css/chat-input.css'; import '../../../eveai_chat_client/static/assets/css/chat-message.css'; import '../../../eveai_chat_client/static/assets/css/form.css'; import '../../../eveai_chat_client/static/assets/css/form-message.css'; // Dependencies import { createApp, version } from 'vue'; import { marked } from 'marked'; import { FormField } from '../../../../../../../../../Users/josako/Library/Application Support/JetBrains/PyCharm2025.1/scratches/old js files/FormField.js'; // Import LanguageProvider for sidebar translation support import { createLanguageProvider, LANGUAGE_PROVIDER_KEY } from '../../../eveai_chat_client/static/assets/js/services/LanguageProvider.js'; // Vue en andere bibliotheken beschikbaar maken window.Vue = { createApp, version }; window.marked = marked; // Gebruik barrel export voor componenten import * as Components from '../../../eveai_chat_client/static/assets/vue-components/index.js'; // Maak Components globaal beschikbaar voor debugging window.Components = Components; console.log('Components loaded:', Object.keys(Components)); // Import specifieke componenten import LanguageSelector from '../../../eveai_chat_client/static/assets/vue-components/LanguageSelector.vue'; import ChatApp from '../../../eveai_chat_client/static/assets/vue-components/ChatApp.vue'; import SideBar from '../../../eveai_chat_client/static/assets/vue-components/SideBar.vue'; import MobileHeader from '../../../eveai_chat_client/static/assets/vue-components/MobileHeader.vue'; // Globale Vue error tracking window.addEventListener('error', function(event) { console.error('🚨 [Global Error]', event.error); }); // Wacht tot DOM geladen is document.addEventListener('DOMContentLoaded', function() { // Controleer of chatConfig is ingesteld if (!window.chatConfig) { console.error('chatConfig is niet beschikbaar'); window.chatConfig = {}; } // Initialiseer sidebar (vervangt fillSidebarExplanation en initializeLanguageSelector) initializeSidebar(); // Initialiseer mobile header initializeMobileHeader(); // Initialiseer chat app (simpel) initializeChatApp(); }); /** * Initialiseert de sidebar component */ function initializeSidebar() { const container = document.getElementById('sidebar-container'); if (!container) { console.error('#sidebar-container niet gevonden'); return; } try { // Maak props voor de component const props = { tenantMake: { name: window.chatConfig.tenantMake?.name || '', logo_url: window.chatConfig.tenantMake?.logo_url || '', subtitle: window.chatConfig.tenantMake?.subtitle || '' }, explanationText: window.chatConfig.explanation || '', initialLanguage: window.chatConfig.language || 'nl', supportedLanguageDetails: window.chatConfig.supportedLanguageDetails || {}, allowedLanguages: window.chatConfig.allowedLanguages || ['nl', 'en', 'fr', 'de'], apiPrefix: window.chatConfig.apiPrefix || '' }; // Mount de component const app = createApp(SideBar, props); // Create and provide LanguageProvider for sidebar components const initialLanguage = window.chatConfig?.language || 'nl'; const apiPrefix = window.chatConfig?.apiPrefix || ''; const languageProvider = createLanguageProvider(initialLanguage, apiPrefix); app.provide(LANGUAGE_PROVIDER_KEY, languageProvider); // Error handler app.config.errorHandler = (err, vm, info) => { console.error('🚨 [Vue Error in Sidebar]', err); console.error('Component:', vm); console.error('Error Info:', info); }; const mountedApp = app.mount(container); // Listen to language change events and update the sidebar's language provider const languageChangeHandler = (event) => { if (event.detail && event.detail.language) { console.log('Sidebar: Received language change event:', event.detail.language); languageProvider.setLanguage(event.detail.language); } }; document.addEventListener('language-changed', languageChangeHandler); // Store the handler for cleanup if needed mountedApp._languageChangeHandler = languageChangeHandler; console.log('✅ Sidebar component successfully mounted with LanguageProvider'); return mountedApp; } catch (error) { console.error('🚨 [CRITICAL ERROR] Bij initialiseren sidebar:', error); } } /** * Initialiseert de mobile header component */ function initializeMobileHeader() { const container = document.getElementById('mobile-header-container'); if (!container) { console.error('#mobile-header-container niet gevonden'); return; } try { // Maak props voor de component const props = { tenantMake: { name: window.chatConfig.tenantMake?.name || '', logo_url: window.chatConfig.tenantMake?.logo_url || '', subtitle: window.chatConfig.tenantMake?.subtitle || '' }, initialLanguage: window.chatConfig.language || 'nl', supportedLanguageDetails: window.chatConfig.supportedLanguageDetails || {}, allowedLanguages: window.chatConfig.allowedLanguages || ['nl', 'en', 'fr', 'de'], apiPrefix: window.chatConfig.apiPrefix || '' }; // Mount de component const app = createApp(MobileHeader, props); // Create and provide LanguageProvider for mobile header components const initialLanguage = window.chatConfig?.language || 'nl'; const apiPrefix = window.chatConfig?.apiPrefix || ''; const languageProvider = createLanguageProvider(initialLanguage, apiPrefix); app.provide(LANGUAGE_PROVIDER_KEY, languageProvider); // Error handler app.config.errorHandler = (err, vm, info) => { console.error('🚨 [Vue Error in MobileHeader]', err); console.error('Component:', vm); console.error('Error Info:', info); }; const mountedApp = app.mount(container); // Dynamisch de headerhoogte doorgeven aan CSS const updateHeaderHeightVar = () => { const isMobile = window.matchMedia('(max-width: 768px)').matches; if (!isMobile) { document.documentElement.style.removeProperty('--mobile-header-height'); return; } const h = container.offsetHeight || 60; // fallback document.documentElement.style.setProperty('--mobile-header-height', `${h}px`); }; // Initieel instellen en bij gebeurtenissen herberekenen requestAnimationFrame(updateHeaderHeightVar); window.addEventListener('resize', updateHeaderHeightVar); // Listen to language change events and update the mobile header's language provider const languageChangeHandler = (event) => { if (event.detail && event.detail.language) { console.log('MobileHeader: Received language change event:', event.detail.language); languageProvider.setLanguage(event.detail.language); // taalwissel kan headerhoogte veranderen requestAnimationFrame(updateHeaderHeightVar); } }; document.addEventListener('language-changed', languageChangeHandler); // Store the handler for cleanup if needed mountedApp._languageChangeHandler = languageChangeHandler; mountedApp._updateHeaderHeightVar = updateHeaderHeightVar; console.log('✅ MobileHeader component successfully mounted with LanguageProvider en dynamische headerhoogte'); return mountedApp; } catch (error) { console.error('🚨 [CRITICAL ERROR] Bij initialiseren mobile header:', error); } } /** * Initialiseert de chat app (Vue component) */ function initializeChatApp() { const container = document.querySelector('.chat-container'); if (!container) { console.error('🚨 [CRITICAL ERROR] .chat-container niet gevonden'); return; } try { if (!ChatApp) { throw new Error('🚨 [CRITICAL ERROR] ChatApp component niet gevonden'); } // Extra verificatie dat alle sub-componenten beschikbaar zijn if (!Components.MessageHistory || !Components.ChatInput || !Components.TypingIndicator || !Components.ChatMessage) { console.warn('⚠️ [WARN] Niet alle benodigde sub-componenten zijn geladen!'); } // Maak props voor de component const props = { apiPrefix: window.chatConfig.apiPrefix || '', conversationId: window.chatConfig.conversationId || 'default', userId: window.chatConfig.userId || null, userName: window.chatConfig.userName || '', initialLanguage: window.chatConfig.language || 'nl', supportedLanguageDetails: window.chatConfig.supportedLanguageDetails || {}, allowedLanguages: window.chatConfig.allowedLanguages || ['nl', 'en', 'fr', 'de'] }; // Mount de component met alle nodige componenten const app = createApp(ChatApp, props); // SSE verbinding configuratie - injecteren in ChatApp component app.provide('sseConfig', { maxRetries: 3, retryDelay: 2000, handleSseError: function(error, taskId) { console.warn(`SSE verbinding voor task ${taskId} mislukt:`, error); // Fallback naar polling als SSE faalt return this.fallbackToPolling(taskId); }, fallbackToPolling: function(taskId) { console.log(`Fallback naar polling voor task ${taskId}`); // Polling implementatie - elke 3 seconden status checken const pollingInterval = setInterval(() => { const endpoint = `${props.apiPrefix}/api/task_status/${taskId}`; fetch(endpoint) .then(response => { if (!response.ok) throw new Error(`Task status endpoint error: ${response.status}`); return response.json(); }) .then(data => { // Dispatch event om dezelfde event interface als SSE te behouden const mockEvent = new CustomEvent('message', { detail: { data: JSON.stringify(data) } }); document.dispatchEvent(new CustomEvent(`sse:${taskId}:message`, { detail: mockEvent })); // Stop polling als taak klaar is if (data.status === 'completed' || data.status === 'failed' || data.status === 'cancelled') { clearInterval(pollingInterval); } }) .catch(err => console.error('Polling error:', err)); }, 3000); return pollingInterval; } }); // Registreer alle componenten globaal Object.entries(Components).forEach(([name, component]) => { app.component(name, component); }); // Registreer error handler app.config.errorHandler = (err, vm, info) => { console.error('🚨 [Vue Error in ChatApp]', err); console.error('Component:', vm); console.error('Error Info:', info); }; // Mount de component const mountedApp = app.mount(container); // Bewaar referentie globaal voor debugging window.__chatApp = mountedApp; // Bewaar een referentie naar de Vue instantie voor gebruik door andere componenten window.__vueApp = app; } catch (error) { console.error('🚨 [CRITICAL ERROR] Bij initialiseren chat app:', error); console.error('Stack trace:', error.stack); // Fallback naar placeholder container.innerHTML = '
Fout bij het initialiseren van de chat applicatie
'; } } /** * Helper functie om Vue 3 element refs te verwerken * Oplossing voor $el.querySelector problemen */ window.getElementFromRef = function(ref) { if (!ref) return null; // Vue 3 refs zijn reactieve objecten met een .value eigenschap if (ref.value && ref.value instanceof HTMLElement) { return ref.value; } // Directe HTML element refs if (ref instanceof HTMLElement) { return ref; } // Vue 3 component instance (geen $el meer in Vue 3) if (ref.$el && ref.$el instanceof HTMLElement) { return ref.$el; } // Voor template refs van Vue 3 mounted componenten if (typeof ref === 'object' && ref !== null) { const element = ref.el || ref.$el || ref.value; if (element instanceof HTMLElement) { return element; } } return null; } console.log('Chat client modules geladen en gebundeld met moderne ES module structuur.');