@a.izzuddin/ai-chat 0.2.10 → 0.2.13
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/custom-elements.json +87 -6
- package/dist/index.d.mts +30 -4
- package/dist/index.d.ts +30 -4
- package/dist/index.js +196 -32
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +196 -32
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -2
package/custom-elements.json
CHANGED
|
@@ -70,11 +70,6 @@
|
|
|
70
70
|
"kind": "javascript-module",
|
|
71
71
|
"path": "dist/index.js",
|
|
72
72
|
"declarations": [
|
|
73
|
-
{
|
|
74
|
-
"kind": "variable",
|
|
75
|
-
"name": "faqs",
|
|
76
|
-
"default": "void 0"
|
|
77
|
-
},
|
|
78
73
|
{
|
|
79
74
|
"kind": "variable",
|
|
80
75
|
"name": "suggestedQuestions",
|
|
@@ -706,6 +701,36 @@
|
|
|
706
701
|
"default": "''",
|
|
707
702
|
"attribute": "welcome-subtitle"
|
|
708
703
|
},
|
|
704
|
+
{
|
|
705
|
+
"kind": "field",
|
|
706
|
+
"name": "initialQuestionsUrl",
|
|
707
|
+
"privacy": "public",
|
|
708
|
+
"type": {
|
|
709
|
+
"text": "string"
|
|
710
|
+
},
|
|
711
|
+
"default": "''",
|
|
712
|
+
"attribute": "initial-questions-url"
|
|
713
|
+
},
|
|
714
|
+
{
|
|
715
|
+
"kind": "field",
|
|
716
|
+
"name": "language",
|
|
717
|
+
"privacy": "public",
|
|
718
|
+
"type": {
|
|
719
|
+
"text": "string"
|
|
720
|
+
},
|
|
721
|
+
"default": "'en'",
|
|
722
|
+
"attribute": "language"
|
|
723
|
+
},
|
|
724
|
+
{
|
|
725
|
+
"kind": "field",
|
|
726
|
+
"name": "showRelatedFaqs",
|
|
727
|
+
"privacy": "public",
|
|
728
|
+
"type": {
|
|
729
|
+
"text": "boolean"
|
|
730
|
+
},
|
|
731
|
+
"default": "true",
|
|
732
|
+
"attribute": "show-related-faqs"
|
|
733
|
+
},
|
|
709
734
|
{
|
|
710
735
|
"kind": "field",
|
|
711
736
|
"name": "messages",
|
|
@@ -846,6 +871,25 @@
|
|
|
846
871
|
"name": "scrollToBottom",
|
|
847
872
|
"privacy": "private"
|
|
848
873
|
},
|
|
874
|
+
{
|
|
875
|
+
"kind": "method",
|
|
876
|
+
"name": "normalizeSuggestedQuestions",
|
|
877
|
+
"privacy": "private",
|
|
878
|
+
"return": {
|
|
879
|
+
"type": {
|
|
880
|
+
"text": "SuggestedQuestion[] | undefined"
|
|
881
|
+
}
|
|
882
|
+
},
|
|
883
|
+
"parameters": [
|
|
884
|
+
{
|
|
885
|
+
"name": "questions",
|
|
886
|
+
"type": {
|
|
887
|
+
"text": "any"
|
|
888
|
+
}
|
|
889
|
+
}
|
|
890
|
+
],
|
|
891
|
+
"description": "Normalize suggested questions - converts string arrays to SuggestedQuestion objects"
|
|
892
|
+
},
|
|
849
893
|
{
|
|
850
894
|
"kind": "method",
|
|
851
895
|
"name": "handleInput",
|
|
@@ -867,7 +911,20 @@
|
|
|
867
911
|
{
|
|
868
912
|
"name": "question",
|
|
869
913
|
"type": {
|
|
870
|
-
"text": "
|
|
914
|
+
"text": "SuggestedQuestion"
|
|
915
|
+
}
|
|
916
|
+
}
|
|
917
|
+
]
|
|
918
|
+
},
|
|
919
|
+
{
|
|
920
|
+
"kind": "method",
|
|
921
|
+
"name": "handleSuggestedQuestionClick",
|
|
922
|
+
"privacy": "private",
|
|
923
|
+
"parameters": [
|
|
924
|
+
{
|
|
925
|
+
"name": "question",
|
|
926
|
+
"type": {
|
|
927
|
+
"text": "SuggestedQuestion"
|
|
871
928
|
}
|
|
872
929
|
}
|
|
873
930
|
]
|
|
@@ -1050,6 +1107,30 @@
|
|
|
1050
1107
|
},
|
|
1051
1108
|
"default": "''",
|
|
1052
1109
|
"fieldName": "welcomeSubtitle"
|
|
1110
|
+
},
|
|
1111
|
+
{
|
|
1112
|
+
"name": "initial-questions-url",
|
|
1113
|
+
"type": {
|
|
1114
|
+
"text": "string"
|
|
1115
|
+
},
|
|
1116
|
+
"default": "''",
|
|
1117
|
+
"fieldName": "initialQuestionsUrl"
|
|
1118
|
+
},
|
|
1119
|
+
{
|
|
1120
|
+
"name": "language",
|
|
1121
|
+
"type": {
|
|
1122
|
+
"text": "string"
|
|
1123
|
+
},
|
|
1124
|
+
"default": "'en'",
|
|
1125
|
+
"fieldName": "language"
|
|
1126
|
+
},
|
|
1127
|
+
{
|
|
1128
|
+
"name": "show-related-faqs",
|
|
1129
|
+
"type": {
|
|
1130
|
+
"text": "boolean"
|
|
1131
|
+
},
|
|
1132
|
+
"default": "true",
|
|
1133
|
+
"fieldName": "showRelatedFaqs"
|
|
1053
1134
|
}
|
|
1054
1135
|
],
|
|
1055
1136
|
"superclass": {
|
package/dist/index.d.mts
CHANGED
|
@@ -3,15 +3,21 @@ import * as lit from 'lit';
|
|
|
3
3
|
import { LitElement, PropertyValues } from 'lit';
|
|
4
4
|
|
|
5
5
|
interface FAQ {
|
|
6
|
-
|
|
7
|
-
|
|
6
|
+
No: string;
|
|
7
|
+
Question: string;
|
|
8
|
+
}
|
|
9
|
+
interface SuggestedQuestion {
|
|
10
|
+
id?: number;
|
|
11
|
+
question_type?: string;
|
|
12
|
+
question_text: string;
|
|
13
|
+
category?: string;
|
|
8
14
|
}
|
|
9
15
|
interface Message {
|
|
10
16
|
id: string;
|
|
11
17
|
role: 'user' | 'assistant';
|
|
12
18
|
content: string;
|
|
13
19
|
faqs?: FAQ[];
|
|
14
|
-
suggestedQuestions?:
|
|
20
|
+
suggestedQuestions?: SuggestedQuestion[];
|
|
15
21
|
}
|
|
16
22
|
/**
|
|
17
23
|
* AI Chat Web Component
|
|
@@ -70,6 +76,9 @@ declare class AIChat extends LitElement {
|
|
|
70
76
|
botMessageBg: string;
|
|
71
77
|
welcomeMessage: string;
|
|
72
78
|
welcomeSubtitle: string;
|
|
79
|
+
initialQuestionsUrl: string;
|
|
80
|
+
language: string;
|
|
81
|
+
showRelatedFaqs: boolean;
|
|
73
82
|
private messages;
|
|
74
83
|
private input;
|
|
75
84
|
private isLoading;
|
|
@@ -141,6 +150,18 @@ declare class AIChat extends LitElement {
|
|
|
141
150
|
type: StringConstructor;
|
|
142
151
|
attribute: string;
|
|
143
152
|
};
|
|
153
|
+
initialQuestionsUrl: {
|
|
154
|
+
type: StringConstructor;
|
|
155
|
+
attribute: string;
|
|
156
|
+
};
|
|
157
|
+
language: {
|
|
158
|
+
type: StringConstructor;
|
|
159
|
+
attribute: string;
|
|
160
|
+
};
|
|
161
|
+
showRelatedFaqs: {
|
|
162
|
+
type: BooleanConstructor;
|
|
163
|
+
attribute: string;
|
|
164
|
+
};
|
|
144
165
|
};
|
|
145
166
|
constructor();
|
|
146
167
|
private toggleWidget;
|
|
@@ -155,11 +176,16 @@ declare class AIChat extends LitElement {
|
|
|
155
176
|
private loadMessagesFromStorage;
|
|
156
177
|
private clearMessagesFromStorage;
|
|
157
178
|
private formatMessageContent;
|
|
158
|
-
connectedCallback(): void
|
|
179
|
+
connectedCallback(): Promise<void>;
|
|
159
180
|
updated(changedProperties: PropertyValues): void;
|
|
160
181
|
private scrollToBottom;
|
|
182
|
+
/**
|
|
183
|
+
* Normalize suggested questions - converts string arrays to SuggestedQuestion objects
|
|
184
|
+
*/
|
|
185
|
+
private normalizeSuggestedQuestions;
|
|
161
186
|
private handleInput;
|
|
162
187
|
private handleFAQClick;
|
|
188
|
+
private handleSuggestedQuestionClick;
|
|
163
189
|
private handleSubmit;
|
|
164
190
|
private renderChatUI;
|
|
165
191
|
render(): lit_html.TemplateResult<1>;
|
package/dist/index.d.ts
CHANGED
|
@@ -3,15 +3,21 @@ import * as lit from 'lit';
|
|
|
3
3
|
import { LitElement, PropertyValues } from 'lit';
|
|
4
4
|
|
|
5
5
|
interface FAQ {
|
|
6
|
-
|
|
7
|
-
|
|
6
|
+
No: string;
|
|
7
|
+
Question: string;
|
|
8
|
+
}
|
|
9
|
+
interface SuggestedQuestion {
|
|
10
|
+
id?: number;
|
|
11
|
+
question_type?: string;
|
|
12
|
+
question_text: string;
|
|
13
|
+
category?: string;
|
|
8
14
|
}
|
|
9
15
|
interface Message {
|
|
10
16
|
id: string;
|
|
11
17
|
role: 'user' | 'assistant';
|
|
12
18
|
content: string;
|
|
13
19
|
faqs?: FAQ[];
|
|
14
|
-
suggestedQuestions?:
|
|
20
|
+
suggestedQuestions?: SuggestedQuestion[];
|
|
15
21
|
}
|
|
16
22
|
/**
|
|
17
23
|
* AI Chat Web Component
|
|
@@ -70,6 +76,9 @@ declare class AIChat extends LitElement {
|
|
|
70
76
|
botMessageBg: string;
|
|
71
77
|
welcomeMessage: string;
|
|
72
78
|
welcomeSubtitle: string;
|
|
79
|
+
initialQuestionsUrl: string;
|
|
80
|
+
language: string;
|
|
81
|
+
showRelatedFaqs: boolean;
|
|
73
82
|
private messages;
|
|
74
83
|
private input;
|
|
75
84
|
private isLoading;
|
|
@@ -141,6 +150,18 @@ declare class AIChat extends LitElement {
|
|
|
141
150
|
type: StringConstructor;
|
|
142
151
|
attribute: string;
|
|
143
152
|
};
|
|
153
|
+
initialQuestionsUrl: {
|
|
154
|
+
type: StringConstructor;
|
|
155
|
+
attribute: string;
|
|
156
|
+
};
|
|
157
|
+
language: {
|
|
158
|
+
type: StringConstructor;
|
|
159
|
+
attribute: string;
|
|
160
|
+
};
|
|
161
|
+
showRelatedFaqs: {
|
|
162
|
+
type: BooleanConstructor;
|
|
163
|
+
attribute: string;
|
|
164
|
+
};
|
|
144
165
|
};
|
|
145
166
|
constructor();
|
|
146
167
|
private toggleWidget;
|
|
@@ -155,11 +176,16 @@ declare class AIChat extends LitElement {
|
|
|
155
176
|
private loadMessagesFromStorage;
|
|
156
177
|
private clearMessagesFromStorage;
|
|
157
178
|
private formatMessageContent;
|
|
158
|
-
connectedCallback(): void
|
|
179
|
+
connectedCallback(): Promise<void>;
|
|
159
180
|
updated(changedProperties: PropertyValues): void;
|
|
160
181
|
private scrollToBottom;
|
|
182
|
+
/**
|
|
183
|
+
* Normalize suggested questions - converts string arrays to SuggestedQuestion objects
|
|
184
|
+
*/
|
|
185
|
+
private normalizeSuggestedQuestions;
|
|
161
186
|
private handleInput;
|
|
162
187
|
private handleFAQClick;
|
|
188
|
+
private handleSuggestedQuestionClick;
|
|
163
189
|
private handleSubmit;
|
|
164
190
|
private renderChatUI;
|
|
165
191
|
render(): lit_html.TemplateResult<1>;
|
package/dist/index.js
CHANGED
|
@@ -16,7 +16,7 @@ var __decorateClass = (decorators, target, key, kind) => {
|
|
|
16
16
|
if (kind && result) __defProp(target, key, result);
|
|
17
17
|
return result;
|
|
18
18
|
};
|
|
19
|
-
var VERSION = "0.2.
|
|
19
|
+
var VERSION = "0.2.13";
|
|
20
20
|
exports.AIChat = class AIChat extends lit.LitElement {
|
|
21
21
|
constructor() {
|
|
22
22
|
super();
|
|
@@ -37,6 +37,9 @@ exports.AIChat = class AIChat extends lit.LitElement {
|
|
|
37
37
|
this.botMessageBg = "#F5F5F5";
|
|
38
38
|
this.welcomeMessage = "How can I help you today?";
|
|
39
39
|
this.welcomeSubtitle = "";
|
|
40
|
+
this.initialQuestionsUrl = "";
|
|
41
|
+
this.language = "en";
|
|
42
|
+
this.showRelatedFaqs = true;
|
|
40
43
|
this.messages = [];
|
|
41
44
|
this.input = "";
|
|
42
45
|
this.isLoading = false;
|
|
@@ -80,29 +83,38 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
80
83
|
saveMessagesToStorage() {
|
|
81
84
|
try {
|
|
82
85
|
const storageKey = this.getStorageKey();
|
|
83
|
-
|
|
86
|
+
sessionStorage.setItem(storageKey, JSON.stringify(this.messages));
|
|
87
|
+
sessionStorage.setItem("ai-chat-last-session-id", this.sessionId);
|
|
84
88
|
} catch (error) {
|
|
85
|
-
console.warn("Failed to save messages to
|
|
89
|
+
console.warn("Failed to save messages to sessionStorage:", error);
|
|
86
90
|
}
|
|
87
91
|
}
|
|
88
92
|
loadMessagesFromStorage() {
|
|
89
93
|
try {
|
|
94
|
+
const lastSessionId = sessionStorage.getItem("ai-chat-last-session-id");
|
|
95
|
+
if (lastSessionId && lastSessionId !== this.sessionId) {
|
|
96
|
+
console.log(`\u{1F504} Session changed from "${lastSessionId}" to "${this.sessionId}", clearing old messages`);
|
|
97
|
+
const oldStorageKey = `ai-chat-messages-${lastSessionId}`;
|
|
98
|
+
sessionStorage.removeItem(oldStorageKey);
|
|
99
|
+
sessionStorage.setItem("ai-chat-last-session-id", this.sessionId);
|
|
100
|
+
return null;
|
|
101
|
+
}
|
|
90
102
|
const storageKey = this.getStorageKey();
|
|
91
|
-
const saved =
|
|
103
|
+
const saved = sessionStorage.getItem(storageKey);
|
|
92
104
|
if (saved) {
|
|
93
105
|
return JSON.parse(saved);
|
|
94
106
|
}
|
|
95
107
|
} catch (error) {
|
|
96
|
-
console.warn("Failed to load messages from
|
|
108
|
+
console.warn("Failed to load messages from sessionStorage:", error);
|
|
97
109
|
}
|
|
98
110
|
return null;
|
|
99
111
|
}
|
|
100
112
|
clearMessagesFromStorage() {
|
|
101
113
|
try {
|
|
102
114
|
const storageKey = this.getStorageKey();
|
|
103
|
-
|
|
115
|
+
sessionStorage.removeItem(storageKey);
|
|
104
116
|
} catch (error) {
|
|
105
|
-
console.warn("Failed to clear messages from
|
|
117
|
+
console.warn("Failed to clear messages from sessionStorage:", error);
|
|
106
118
|
}
|
|
107
119
|
}
|
|
108
120
|
formatMessageContent(content) {
|
|
@@ -186,22 +198,59 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
186
198
|
}
|
|
187
199
|
return formattedContent;
|
|
188
200
|
}
|
|
189
|
-
connectedCallback() {
|
|
201
|
+
async connectedCallback() {
|
|
190
202
|
super.connectedCallback();
|
|
191
203
|
const savedMessages = this.loadMessagesFromStorage();
|
|
192
204
|
if (this.initialMessages && this.initialMessages.length > 0) {
|
|
193
205
|
this.messages = [...this.initialMessages];
|
|
194
206
|
} else if (savedMessages && savedMessages.length > 0) {
|
|
195
207
|
this.messages = savedMessages;
|
|
196
|
-
} else
|
|
197
|
-
|
|
208
|
+
} else {
|
|
209
|
+
let suggestedQuestions = void 0;
|
|
210
|
+
if (this.initialQuestionsUrl) {
|
|
211
|
+
try {
|
|
212
|
+
let fetchUrl = this.initialQuestionsUrl;
|
|
213
|
+
if (this.language) {
|
|
214
|
+
const separator = fetchUrl.includes("?") ? "&" : "?";
|
|
215
|
+
fetchUrl = `${fetchUrl}${separator}language=${this.language}`;
|
|
216
|
+
}
|
|
217
|
+
console.log("\u{1F4E4} Fetching initial questions from:", fetchUrl);
|
|
218
|
+
const response = await fetch(fetchUrl);
|
|
219
|
+
if (response.ok) {
|
|
220
|
+
const data = await response.json();
|
|
221
|
+
console.log("\u{1F4E5} Fetched initial questions:", data);
|
|
222
|
+
let questionsArray = data.questions || data.suggested_questions || data;
|
|
223
|
+
if (Array.isArray(questionsArray) && questionsArray.length > 0) {
|
|
224
|
+
if (typeof questionsArray[0] === "object" && questionsArray[0].question_text) {
|
|
225
|
+
suggestedQuestions = questionsArray.map((q) => ({
|
|
226
|
+
id: q.id,
|
|
227
|
+
question_type: q.question_type,
|
|
228
|
+
question_text: q.question_text,
|
|
229
|
+
category: q.category
|
|
230
|
+
}));
|
|
231
|
+
} else if (typeof questionsArray[0] === "string") {
|
|
232
|
+
suggestedQuestions = questionsArray.map((q) => ({
|
|
233
|
+
question_text: q
|
|
234
|
+
}));
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
console.log("\u2705 Processed suggested questions:", suggestedQuestions);
|
|
238
|
+
}
|
|
239
|
+
} catch (error) {
|
|
240
|
+
console.warn("Failed to fetch initial questions:", error);
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
if (this.welcomeMessage) {
|
|
244
|
+
const welcomeText = this.welcomeSubtitle ? `${this.welcomeMessage}
|
|
198
245
|
|
|
199
246
|
${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
247
|
+
this.messages = [{
|
|
248
|
+
id: "welcome-" + Date.now(),
|
|
249
|
+
role: "assistant",
|
|
250
|
+
content: welcomeText,
|
|
251
|
+
suggestedQuestions
|
|
252
|
+
}];
|
|
253
|
+
}
|
|
205
254
|
}
|
|
206
255
|
}
|
|
207
256
|
updated(changedProperties) {
|
|
@@ -220,14 +269,121 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
220
269
|
}
|
|
221
270
|
}, 100);
|
|
222
271
|
}
|
|
272
|
+
/**
|
|
273
|
+
* Normalize suggested questions - converts string arrays to SuggestedQuestion objects
|
|
274
|
+
*/
|
|
275
|
+
normalizeSuggestedQuestions(questions) {
|
|
276
|
+
if (!questions || !Array.isArray(questions) || questions.length === 0) {
|
|
277
|
+
return void 0;
|
|
278
|
+
}
|
|
279
|
+
if (typeof questions[0] === "object" && questions[0].question_text) {
|
|
280
|
+
return questions;
|
|
281
|
+
}
|
|
282
|
+
if (typeof questions[0] === "string") {
|
|
283
|
+
return questions.map((q) => ({
|
|
284
|
+
question_text: q
|
|
285
|
+
}));
|
|
286
|
+
}
|
|
287
|
+
return void 0;
|
|
288
|
+
}
|
|
223
289
|
handleInput(e) {
|
|
224
290
|
this.input = e.target.value;
|
|
225
291
|
}
|
|
226
|
-
handleFAQClick(question) {
|
|
292
|
+
async handleFAQClick(question) {
|
|
227
293
|
if (this.isLoading) return;
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
294
|
+
if (question.id && question.question_type) {
|
|
295
|
+
await this.handleSuggestedQuestionClick(question);
|
|
296
|
+
} else {
|
|
297
|
+
this.input = question.question_text;
|
|
298
|
+
const submitEvent = new Event("submit", { cancelable: true });
|
|
299
|
+
this.handleSubmit(submitEvent);
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
async handleSuggestedQuestionClick(question) {
|
|
303
|
+
if (!question.id || !question.question_type) return;
|
|
304
|
+
const userMessage = {
|
|
305
|
+
id: Date.now().toString(),
|
|
306
|
+
role: "user",
|
|
307
|
+
content: question.question_text
|
|
308
|
+
};
|
|
309
|
+
this.messages = [...this.messages, userMessage];
|
|
310
|
+
this.isLoading = true;
|
|
311
|
+
this.dispatchEvent(new CustomEvent("message-sent", {
|
|
312
|
+
detail: userMessage,
|
|
313
|
+
bubbles: true,
|
|
314
|
+
composed: true
|
|
315
|
+
}));
|
|
316
|
+
try {
|
|
317
|
+
let baseUrl = "";
|
|
318
|
+
if (this.initialQuestionsUrl) {
|
|
319
|
+
try {
|
|
320
|
+
const urlObj = new URL(this.initialQuestionsUrl);
|
|
321
|
+
baseUrl = `${urlObj.protocol}//${urlObj.host}`;
|
|
322
|
+
} catch {
|
|
323
|
+
baseUrl = "http://43.217.183.120:8080";
|
|
324
|
+
}
|
|
325
|
+
} else {
|
|
326
|
+
baseUrl = "http://43.217.183.120:8080";
|
|
327
|
+
}
|
|
328
|
+
const url = `${baseUrl}/api/questions/${question.id}?question_type=${question.question_type}`;
|
|
329
|
+
console.log("\u{1F4E4} Calling suggested question API:", url);
|
|
330
|
+
const response = await fetch(url, {
|
|
331
|
+
method: "GET",
|
|
332
|
+
headers: { "Content-Type": "application/json" }
|
|
333
|
+
});
|
|
334
|
+
if (!response.ok) {
|
|
335
|
+
const errorText = await response.text();
|
|
336
|
+
throw new Error(`Backend error: ${response.status} ${errorText}`);
|
|
337
|
+
}
|
|
338
|
+
const data = await response.json();
|
|
339
|
+
console.log("\u{1F50D} Suggested question API response:", data);
|
|
340
|
+
let responseText = "No response from agent";
|
|
341
|
+
let suggestedQuestions = void 0;
|
|
342
|
+
if (data && typeof data === "object") {
|
|
343
|
+
if (data.question && data.question.answer_text) {
|
|
344
|
+
responseText = data.question.answer_text;
|
|
345
|
+
}
|
|
346
|
+
if (data.related_questions && Array.isArray(data.related_questions) && data.related_questions.length > 0) {
|
|
347
|
+
if (typeof data.related_questions[0] === "object" && data.related_questions[0].question_text) {
|
|
348
|
+
suggestedQuestions = data.related_questions.map((q) => ({
|
|
349
|
+
id: q.id,
|
|
350
|
+
question_type: q.question_type,
|
|
351
|
+
question_text: q.question_text,
|
|
352
|
+
category: q.category
|
|
353
|
+
}));
|
|
354
|
+
}
|
|
355
|
+
}
|
|
356
|
+
}
|
|
357
|
+
const assistantMessage = {
|
|
358
|
+
id: (Date.now() + 1).toString(),
|
|
359
|
+
role: "assistant",
|
|
360
|
+
content: responseText,
|
|
361
|
+
suggestedQuestions
|
|
362
|
+
};
|
|
363
|
+
this.messages = [...this.messages, assistantMessage];
|
|
364
|
+
this.dispatchEvent(new CustomEvent("response-received", {
|
|
365
|
+
detail: assistantMessage,
|
|
366
|
+
bubbles: true,
|
|
367
|
+
composed: true
|
|
368
|
+
}));
|
|
369
|
+
} catch (err) {
|
|
370
|
+
console.error("Suggested question API failed:", err);
|
|
371
|
+
const errorMessage = {
|
|
372
|
+
id: (Date.now() + 1).toString(),
|
|
373
|
+
role: "assistant",
|
|
374
|
+
content: `Error: ${err instanceof Error ? err.message : "Unknown error"}
|
|
375
|
+
|
|
376
|
+
Please check your API endpoint configuration.`
|
|
377
|
+
};
|
|
378
|
+
this.messages = [...this.messages, errorMessage];
|
|
379
|
+
this.dispatchEvent(new CustomEvent("error", {
|
|
380
|
+
detail: err,
|
|
381
|
+
bubbles: true,
|
|
382
|
+
composed: true
|
|
383
|
+
}));
|
|
384
|
+
} finally {
|
|
385
|
+
this.isLoading = false;
|
|
386
|
+
}
|
|
231
387
|
}
|
|
232
388
|
async handleSubmit(e) {
|
|
233
389
|
e.preventDefault();
|
|
@@ -276,14 +432,14 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
276
432
|
if (innerData && innerData.response && typeof innerData.response === "string") {
|
|
277
433
|
responseText = innerData.response;
|
|
278
434
|
faqs = innerData.faq_used || innerData.faqs_used || void 0;
|
|
279
|
-
suggestedQuestions = innerData.suggested_follow_ups || innerData.suggested_questions
|
|
435
|
+
suggestedQuestions = this.normalizeSuggestedQuestions(innerData.suggested_follow_ups || innerData.suggested_questions);
|
|
280
436
|
console.log("\u2705 Extracted text length:", responseText.length);
|
|
281
437
|
console.log("\u2705 Extracted FAQs count:", faqs?.length || 0);
|
|
282
438
|
console.log("\u2705 Extracted suggested questions count:", suggestedQuestions?.length || 0);
|
|
283
439
|
} else {
|
|
284
440
|
responseText = data.response;
|
|
285
441
|
faqs = data.faq_used || data.faqs_used || void 0;
|
|
286
|
-
suggestedQuestions = data.suggested_follow_ups || data.suggested_questions
|
|
442
|
+
suggestedQuestions = this.normalizeSuggestedQuestions(data.suggested_follow_ups || data.suggested_questions);
|
|
287
443
|
}
|
|
288
444
|
} catch (parseError) {
|
|
289
445
|
console.warn("\u26A0\uFE0F JSON.parse failed, using regex extraction...", parseError);
|
|
@@ -320,7 +476,8 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
320
476
|
const suggestedMatch = data.response.match(suggestedPattern);
|
|
321
477
|
if (suggestedMatch) {
|
|
322
478
|
try {
|
|
323
|
-
|
|
479
|
+
const parsedQuestions = JSON.parse(suggestedMatch[1]);
|
|
480
|
+
suggestedQuestions = this.normalizeSuggestedQuestions(parsedQuestions);
|
|
324
481
|
console.log("\u2705 Extracted suggested questions, count:", suggestedQuestions?.length || 0);
|
|
325
482
|
} catch {
|
|
326
483
|
console.log("\u26A0\uFE0F Could not parse suggested questions, trying multiline...");
|
|
@@ -328,7 +485,8 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
328
485
|
const suggestedMultiMatch = data.response.match(suggestedMultiPattern);
|
|
329
486
|
if (suggestedMultiMatch) {
|
|
330
487
|
try {
|
|
331
|
-
|
|
488
|
+
const parsedQuestions = JSON.parse(suggestedMultiMatch[1]);
|
|
489
|
+
suggestedQuestions = this.normalizeSuggestedQuestions(parsedQuestions);
|
|
332
490
|
console.log("\u2705 Extracted multi-line suggested questions, count:", suggestedQuestions?.length || 0);
|
|
333
491
|
} catch {
|
|
334
492
|
suggestedQuestions = void 0;
|
|
@@ -341,7 +499,7 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
341
499
|
console.log("\u{1F4C4} Direct text response (not JSON)");
|
|
342
500
|
responseText = data.response;
|
|
343
501
|
faqs = data.faq_used || data.faqs_used || void 0;
|
|
344
|
-
suggestedQuestions = data.suggested_follow_ups || data.suggested_questions
|
|
502
|
+
suggestedQuestions = this.normalizeSuggestedQuestions(data.suggested_follow_ups || data.suggested_questions);
|
|
345
503
|
}
|
|
346
504
|
} else if (typeof data === "string") {
|
|
347
505
|
console.log("\u{1F4C4} Response is a plain string");
|
|
@@ -350,7 +508,7 @@ ${this.welcomeSubtitle}` : this.welcomeMessage;
|
|
|
350
508
|
console.warn("\u26A0\uFE0F Unexpected format, using fallback");
|
|
351
509
|
responseText = data.message || data.answer || "Error: Unexpected response format";
|
|
352
510
|
faqs = data.faq_used || data.faqs_used || void 0;
|
|
353
|
-
suggestedQuestions = data.suggested_follow_ups || data.suggested_questions
|
|
511
|
+
suggestedQuestions = this.normalizeSuggestedQuestions(data.suggested_follow_ups || data.suggested_questions);
|
|
354
512
|
}
|
|
355
513
|
console.log("\u{1F3AF} Final responseText length:", responseText.length);
|
|
356
514
|
console.log("\u{1F3AF} Final responseText preview:", responseText.substring(0, 100));
|
|
@@ -419,13 +577,13 @@ Please check your API endpoint configuration.`
|
|
|
419
577
|
</div>
|
|
420
578
|
<div class="message-content">
|
|
421
579
|
<div class="message-text">${unsafeHtml_js.unsafeHTML(this.formatMessageContent(msg.content))}</div>
|
|
422
|
-
${msg.role === "assistant" && msg.faqs && msg.faqs.length > 0 ? lit.html`
|
|
580
|
+
${msg.role === "assistant" && this.showRelatedFaqs && msg.faqs && msg.faqs.length > 0 ? lit.html`
|
|
423
581
|
<div class="faq-section">
|
|
424
582
|
<p class="faq-title">Related FAQs:</p>
|
|
425
583
|
<ul class="faq-list">
|
|
426
584
|
${msg.faqs.map((faq) => lit.html`
|
|
427
585
|
<li class="faq-item-static">
|
|
428
|
-
${faq.
|
|
586
|
+
${faq.Question}
|
|
429
587
|
</li>
|
|
430
588
|
`)}
|
|
431
589
|
</ul>
|
|
@@ -437,7 +595,7 @@ Please check your API endpoint configuration.`
|
|
|
437
595
|
<ul class="faq-list">
|
|
438
596
|
${msg.suggestedQuestions.map((question) => lit.html`
|
|
439
597
|
<li class="faq-item" @click=${() => this.handleFAQClick(question)}>
|
|
440
|
-
${question}
|
|
598
|
+
${question.question_text}
|
|
441
599
|
</li>
|
|
442
600
|
`)}
|
|
443
601
|
</ul>
|
|
@@ -603,9 +761,12 @@ exports.AIChat.styles = lit.css`
|
|
|
603
761
|
}
|
|
604
762
|
|
|
605
763
|
.widget-button-icon {
|
|
606
|
-
width:
|
|
607
|
-
height:
|
|
608
|
-
|
|
764
|
+
width: 100%;
|
|
765
|
+
height: 100%;
|
|
766
|
+
max-width: 60px;
|
|
767
|
+
max-height: 60px;
|
|
768
|
+
object-fit: contain;
|
|
769
|
+
border-radius: 50%;
|
|
609
770
|
}
|
|
610
771
|
|
|
611
772
|
.widget-window {
|
|
@@ -1298,7 +1459,10 @@ exports.AIChat.properties = {
|
|
|
1298
1459
|
userMessageBg: { type: String, attribute: "user-message-bg" },
|
|
1299
1460
|
botMessageBg: { type: String, attribute: "bot-message-bg" },
|
|
1300
1461
|
welcomeMessage: { type: String, attribute: "welcome-message" },
|
|
1301
|
-
welcomeSubtitle: { type: String, attribute: "welcome-subtitle" }
|
|
1462
|
+
welcomeSubtitle: { type: String, attribute: "welcome-subtitle" },
|
|
1463
|
+
initialQuestionsUrl: { type: String, attribute: "initial-questions-url" },
|
|
1464
|
+
language: { type: String, attribute: "language" },
|
|
1465
|
+
showRelatedFaqs: { type: Boolean, attribute: "show-related-faqs" }
|
|
1302
1466
|
};
|
|
1303
1467
|
__decorateClass([
|
|
1304
1468
|
decorators_js.state()
|