1/** 2 * Application â generic base class 3 * 4 * Provides two utility methods shared by all entry points: 5 * - ensureSessionCookie() â creates a guest session cookie on the first visit 6 * - readConfig() â reads data-* attributes from the container element 7 * 8 * Each entry point should extend this class and supplies its own containerId, EventManager instance, and manager setup 9 */ 10export class Application { 11 /** 12 * @param {string} containerId â ID of the root DOM element for this plugin 13 */ 14 constructor(containerId) { 15 this.container = document.getElementById(containerId); 16 if (!this.container) return; 17 18 this.ensureSessionCookie(); 19 this.config = this.readConfig(); 20 } 21 22 /** 23 * Read plugin configuration from data-* attributes on the container 24 * @returns {Object} 25 */ 26 readConfig() { 27 const c = this.container; 28 return { 29 messageEndpoint: c.dataset.apiMessage || '', 30 clearEndpoint: c.dataset.apiClear || '', 31 maxLength: c.dataset.maxLength || '5000', 32 honeypotField: c.dataset.honeypotField || 'email', 33 renderTime: c.dataset.renderTime || '0', 34 profile: c.dataset.profile || '', 35 showSourcesTitle: c.dataset.showSourcesTitle !== 'false', 36 preferredLanguage: c.dataset.siteLanguage || document.documentElement.lang || '' 37 }; 38 } 39 40 /** 41 * Ensure a chatbot session cookie exists for server-side history persistence 42 * Creates a random guest_ cookie on first visit, valid for 1 year 43 * Skipped when the user is already identified (server sets a user_ cookie) 44 */ 45 ensureSessionCookie() { 46 const cookieName = 'chatbot_session'; 47 const existing = document.cookie 48 .split('; ') 49 .find(row => row.startsWith(cookieName + '=')); 50 51 if (!existing) { 52 // Generate random session ID 53 const sessionId = 'guest_' + Array.from(crypto.getRandomValues(new Uint8Array(16))) 54 .map(b => b.toString(16).padStart(2, '0')) 55 .join(''); 56 57 // Set cookie for 1 year 58 const expires = new Date(); 59 expires.setFullYear(expires.getFullYear() + 1); 60 61 document.cookie = `${cookieName}=${sessionId}; expires=${expires.toUTCString()}; path=/; SameSite=Lax; Secure`; 62 } 63 } 64}
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.