@gengage/assistant-fe 0.4.3 → 0.4.5
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/README.md +3 -0
- package/dist/chat/catalog.d.ts +29 -0
- package/dist/chat/components/ChatDrawer.d.ts +9 -13
- package/dist/chat/components/PanelRestoreCard.d.ts +4 -0
- package/dist/chat/history-storage.d.ts +85 -0
- package/dist/chat/index.d.ts +31 -3
- package/dist/chat/panel-manager.d.ts +1 -1
- package/dist/chat/session-persistence.d.ts +2 -2
- package/dist/chat/types.d.ts +10 -2
- package/dist/chat-B1lLKIxj.js +7996 -0
- package/dist/chat.iife.js +61 -36
- package/dist/chat.js +1 -1
- package/dist/common/indexed-db.d.ts +5 -1
- package/dist/{common-DDQyFEcK.js → common-C5e2gLuG.js} +2 -2
- package/dist/common.js +4 -4
- package/dist/index.js +6 -6
- package/dist/{native-webview-CwQr4fXv.js → native-webview-niMtkiHX.js} +4 -4
- package/dist/native.iife.js +57 -32
- package/dist/native.js +1 -1
- package/dist/{qna-CQugVOHy.js → qna-C5Ok3wd0.js} +1 -1
- package/dist/qna.iife.js +50 -25
- package/dist/qna.js +1 -1
- package/dist/{schemas-JFGRVTVz.js → schemas-JpRGzRQT.js} +1717 -1361
- package/dist/{simrel-DjzpRZmZ.js → simrel-K2TGFi1r.js} +1 -1
- package/dist/simrel.iife.js +54 -29
- package/dist/simrel.js +1 -1
- package/package.json +2 -1
- package/dist/chat/components/ThumbnailsColumn.d.ts +0 -24
- package/dist/chat-sb3DK_dL.js +0 -7524
package/README.md
CHANGED
|
@@ -91,6 +91,8 @@ See [docs/native-mobile-sdk.md](docs/native-mobile-sdk.md) for iOS WKWebView, An
|
|
|
91
91
|
| **SimBut** | `@gengage/assistant-fe/simbut` | PDP image-overlay pill that opens a `findSimilar` flow for the current product |
|
|
92
92
|
| **Native** | `@gengage/assistant-fe/native` | Android/iOS WebView bridge + overlay bootstrap |
|
|
93
93
|
|
|
94
|
+
The chat widget includes a built-in history entry point in the header. Past chat sessions are stored per account/user in `localStorage`, while the active session restore cache continues to use IndexedDB for cross-navigation handoff flows.
|
|
95
|
+
|
|
94
96
|
---
|
|
95
97
|
|
|
96
98
|
## Customization
|
|
@@ -121,6 +123,7 @@ npm run koctascomtr # Merchant shortcut with the seed
|
|
|
121
123
|
npm run trendyolcom # Another merchant shortcut using its default PDP SKU
|
|
122
124
|
npm run typecheck # TypeScript strict check
|
|
123
125
|
npm run test # Unit tests
|
|
126
|
+
npm run test:chat-history # Targeted history + restore regression suite
|
|
124
127
|
npm run build # Build to dist/
|
|
125
128
|
npm run catalog # Visual component catalog at :3002
|
|
126
129
|
npm run docs:build # Build contributor docs with VitePress
|
package/dist/chat/catalog.d.ts
CHANGED
|
@@ -365,6 +365,19 @@ export declare const HandoffNoticeSchema: z.ZodObject<{
|
|
|
365
365
|
products_discussed: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
366
366
|
user_sentiment: z.ZodOptional<z.ZodString>;
|
|
367
367
|
}, z.core.$strip>;
|
|
368
|
+
export declare const PanelRestoreCardSchema: z.ZodObject<{
|
|
369
|
+
eyebrow: z.ZodOptional<z.ZodString>;
|
|
370
|
+
title: z.ZodOptional<z.ZodString>;
|
|
371
|
+
showTitle: z.ZodOptional<z.ZodBoolean>;
|
|
372
|
+
ctaLabel: z.ZodOptional<z.ZodString>;
|
|
373
|
+
panelMessageId: z.ZodString;
|
|
374
|
+
highlightMessageId: z.ZodOptional<z.ZodString>;
|
|
375
|
+
threadId: z.ZodOptional<z.ZodString>;
|
|
376
|
+
products: z.ZodOptional<z.ZodArray<z.ZodObject<{
|
|
377
|
+
imageUrl: z.ZodOptional<z.ZodString>;
|
|
378
|
+
name: z.ZodOptional<z.ZodString>;
|
|
379
|
+
}, z.core.$strip>>>;
|
|
380
|
+
}, z.core.$strip>;
|
|
368
381
|
export declare const PhotoAnalysisCardSchema: z.ZodObject<{
|
|
369
382
|
summary: z.ZodString;
|
|
370
383
|
strengths: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
@@ -769,6 +782,22 @@ export declare const chatCatalog: {
|
|
|
769
782
|
}, z.core.$strip>;
|
|
770
783
|
readonly description: "A notice shown when the conversation is escalated to a human agent.";
|
|
771
784
|
};
|
|
785
|
+
readonly PanelRestoreCard: {
|
|
786
|
+
readonly schema: z.ZodObject<{
|
|
787
|
+
eyebrow: z.ZodOptional<z.ZodString>;
|
|
788
|
+
title: z.ZodOptional<z.ZodString>;
|
|
789
|
+
showTitle: z.ZodOptional<z.ZodBoolean>;
|
|
790
|
+
ctaLabel: z.ZodOptional<z.ZodString>;
|
|
791
|
+
panelMessageId: z.ZodString;
|
|
792
|
+
highlightMessageId: z.ZodOptional<z.ZodString>;
|
|
793
|
+
threadId: z.ZodOptional<z.ZodString>;
|
|
794
|
+
products: z.ZodOptional<z.ZodArray<z.ZodObject<{
|
|
795
|
+
imageUrl: z.ZodOptional<z.ZodString>;
|
|
796
|
+
name: z.ZodOptional<z.ZodString>;
|
|
797
|
+
}, z.core.$strip>>>;
|
|
798
|
+
}, z.core.$strip>;
|
|
799
|
+
readonly description: "A frontend-owned transcript card that reopens a related panel snapshot.";
|
|
800
|
+
};
|
|
772
801
|
readonly PhotoAnalysisCard: {
|
|
773
802
|
readonly schema: z.ZodObject<{
|
|
774
803
|
summary: z.ZodString;
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import { ChatI18n, ChatMessage } from '../types.js';
|
|
2
|
-
import { ThumbnailEntry } from './ThumbnailsColumn.js';
|
|
3
2
|
/** Generic fallback icon (right-arrow) used when a pill specifies an icon name not in the map. */
|
|
4
3
|
declare const DEFAULT_ACTION_ICON = "<svg viewBox=\"0 0 16 16\" class=\"gengage-chat-icon\"><path d=\"M3 8h10M9 4l4 4-4 4\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.5\" stroke-linecap=\"round\" stroke-linejoin=\"round\"/></svg>";
|
|
5
4
|
/** SVG icon map for suggested action chips/pills. Keys match backend icon names. */
|
|
@@ -31,6 +30,8 @@ export interface ChatDrawerOptions {
|
|
|
31
30
|
/** When true, render the header favorites (heart) button. */
|
|
32
31
|
showHeaderFavorites?: boolean | undefined;
|
|
33
32
|
onFavoritesClick?: (() => void) | undefined;
|
|
33
|
+
/** Callback fired when the history button in the header is clicked. */
|
|
34
|
+
onHistoryClick?: (() => void) | undefined;
|
|
34
35
|
/** Callback fired when the panel back button is clicked. */
|
|
35
36
|
onPanelBack?: (() => void) | undefined;
|
|
36
37
|
/** Callback fired when the panel forward button is clicked. */
|
|
@@ -48,10 +49,10 @@ export interface ChatDrawerOptions {
|
|
|
48
49
|
getMobileState?: (() => 'half' | 'full') | undefined;
|
|
49
50
|
/** Returns true when the chat is displayed as a mobile bottom-sheet. Used to keep the side-panel back button always enabled. */
|
|
50
51
|
getMobileViewport?: (() => boolean) | undefined;
|
|
51
|
-
/** Callback fired when a product thumbnail is clicked (for thread rollback). */
|
|
52
|
-
onThumbnailClick?: ((threadId: string) => void) | undefined;
|
|
53
52
|
/** Callback fired when a link in bot HTML is clicked. */
|
|
54
53
|
onLinkClick?: ((url: string) => void) | undefined;
|
|
54
|
+
/** Render a frontend-owned message UI payload inside the bubble, when present. */
|
|
55
|
+
renderMessageUISpec?: ((message: ChatMessage) => HTMLElement | null) | undefined;
|
|
55
56
|
/** Enable voice input (Web Speech API STT). Default: false. */
|
|
56
57
|
voiceEnabled?: boolean | undefined;
|
|
57
58
|
/** BCP 47 language for speech recognition. Default: 'tr-TR'. */
|
|
@@ -87,9 +88,7 @@ export declare class ChatDrawer {
|
|
|
87
88
|
private _panelEl;
|
|
88
89
|
private _panelVisible;
|
|
89
90
|
private _panelCollapsed;
|
|
90
|
-
private _dividerPreviewEnabled;
|
|
91
91
|
private _dividerEl;
|
|
92
|
-
private _dividerPreviewEl;
|
|
93
92
|
private _onPanelToggle;
|
|
94
93
|
private _onHostShellSync;
|
|
95
94
|
private _pendingAttachment;
|
|
@@ -105,7 +104,6 @@ export declare class ChatDrawer {
|
|
|
105
104
|
private _userScrolledUp;
|
|
106
105
|
private _scrollLockedUntil;
|
|
107
106
|
private _inputChipsEl;
|
|
108
|
-
private _thumbnailsColumn;
|
|
109
107
|
private _panelFloatingEl;
|
|
110
108
|
/** Mobile: overlay host for comparison dock (above panel scroll; avoids transformed panel containing block). */
|
|
111
109
|
private _comparisonDockSlotEl;
|
|
@@ -227,7 +225,7 @@ export declare class ChatDrawer {
|
|
|
227
225
|
/**
|
|
228
226
|
* Targeted content swap for an already-visible panel. Replaces the skeleton
|
|
229
227
|
* or the current content element with `el`, leaving topbar / AI zone /
|
|
230
|
-
*
|
|
228
|
+
* floating element attached. Also resets topbar actions
|
|
231
229
|
* because the incoming content provides its own toolbar.
|
|
232
230
|
*/
|
|
233
231
|
private _swapPanelContent;
|
|
@@ -242,7 +240,7 @@ export declare class ChatDrawer {
|
|
|
242
240
|
resyncPanelTopBarFromCurrentContent(): void;
|
|
243
241
|
/** Whether the panel is currently visible (may be empty). */
|
|
244
242
|
isPanelVisible(): boolean;
|
|
245
|
-
/** Whether the panel is currently visible and has rendered content
|
|
243
|
+
/** Whether the panel is currently visible and has rendered content beyond chrome elements. */
|
|
246
244
|
hasPanelContent(): boolean;
|
|
247
245
|
/** Whether panel currently shows loading skeleton blocks. */
|
|
248
246
|
isPanelLoading(): boolean;
|
|
@@ -260,6 +258,7 @@ export declare class ChatDrawer {
|
|
|
260
258
|
* Keeps `_panelCollapsed` untouched so user collapse preference survives future panel renders.
|
|
261
259
|
*/
|
|
262
260
|
clearPanel(): void;
|
|
261
|
+
private _syncComparisonDockVisibility;
|
|
263
262
|
/**
|
|
264
263
|
* Mobile-only slot (see CSS): pins the comparison dock above panel scroll.
|
|
265
264
|
* Pass null to clear.
|
|
@@ -271,6 +270,7 @@ export declare class ChatDrawer {
|
|
|
271
270
|
*/
|
|
272
271
|
hideMobilePanel(): void;
|
|
273
272
|
private _showMobilePanelFromBtn;
|
|
273
|
+
showMobilePanel(): void;
|
|
274
274
|
/** Expand panel without locking — user can still toggle via divider. */
|
|
275
275
|
expandPanel(): void;
|
|
276
276
|
/**
|
|
@@ -284,6 +284,7 @@ export declare class ChatDrawer {
|
|
|
284
284
|
* case subsequent DOM mutations (appended children, layout) shift it.
|
|
285
285
|
*/
|
|
286
286
|
private _smoothScrollPanelListToTop;
|
|
287
|
+
private _getChoicePrompterRevealScrollThreshold;
|
|
287
288
|
/** Update scroll affordance (bottom fade gradient) on the panel. */
|
|
288
289
|
private _updateScrollAffordance;
|
|
289
290
|
/** Horizontal swipe on conversation/panel areas to toggle the panel (mobile only). */
|
|
@@ -294,7 +295,6 @@ export declare class ChatDrawer {
|
|
|
294
295
|
isPanelCollapsed(): boolean;
|
|
295
296
|
/** Programmatically set panel collapsed state. */
|
|
296
297
|
setPanelCollapsed(collapsed: boolean): void;
|
|
297
|
-
setDividerPreviewEnabled(enabled: boolean): void;
|
|
298
298
|
/** Save panel collapsed state to sessionStorage. */
|
|
299
299
|
persistPanelState(accountId: string): void;
|
|
300
300
|
/** Restore panel collapsed state from sessionStorage. Returns true when restored as collapsed. */
|
|
@@ -347,10 +347,6 @@ export declare class ChatDrawer {
|
|
|
347
347
|
}>): void;
|
|
348
348
|
/** Clear input-area chips. */
|
|
349
349
|
clearInputAreaChips(): void;
|
|
350
|
-
setThumbnails(entries: ThumbnailEntry[]): void;
|
|
351
|
-
hideThumbnails(): void;
|
|
352
|
-
private _renderDividerPreview;
|
|
353
|
-
private _syncDividerPreview;
|
|
354
350
|
/** Activate focus trap — Tab/Shift+Tab cycles within the drawer. */
|
|
355
351
|
trapFocus(): void;
|
|
356
352
|
/** Release the focus trap and restore previously focused element. */
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import { UIElement } from '../../common/types.js';
|
|
2
|
+
import { ChatUISpecRenderContext } from '../types.js';
|
|
3
|
+
export declare const FRONTEND_PANEL_RESTORE_ACTION = "frontend_restore_panel_message";
|
|
4
|
+
export declare function renderPanelRestoreCard(element: UIElement, ctx: ChatUISpecRenderContext): HTMLElement;
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
import { BackendContext, UISpec } from '../common/types.js';
|
|
2
|
+
import { ChatMessage } from './types.js';
|
|
3
|
+
type LegacyThumbnailEntry = {
|
|
4
|
+
sku: string;
|
|
5
|
+
imageUrl: string;
|
|
6
|
+
threadId: string;
|
|
7
|
+
};
|
|
8
|
+
export interface StoredHistoryMessage {
|
|
9
|
+
id: string;
|
|
10
|
+
threadId?: string | undefined;
|
|
11
|
+
role: 'user' | 'assistant';
|
|
12
|
+
content?: string | undefined;
|
|
13
|
+
uiSpec?: UISpec | undefined;
|
|
14
|
+
frontendOnly?: boolean | undefined;
|
|
15
|
+
silent?: boolean | undefined;
|
|
16
|
+
renderHint?: string | undefined;
|
|
17
|
+
photoAnalysis?: {
|
|
18
|
+
summary: string;
|
|
19
|
+
strengths?: string[];
|
|
20
|
+
focusPoints?: string[];
|
|
21
|
+
celebStyle?: string;
|
|
22
|
+
celebStyleReason?: string;
|
|
23
|
+
nextQuestion?: string;
|
|
24
|
+
} | undefined;
|
|
25
|
+
timestamp: number;
|
|
26
|
+
status: 'done' | 'error';
|
|
27
|
+
}
|
|
28
|
+
export interface ChatHistoryIndexEntry {
|
|
29
|
+
id: string;
|
|
30
|
+
title: string;
|
|
31
|
+
preview: string;
|
|
32
|
+
createdAt: string;
|
|
33
|
+
updatedAt: string;
|
|
34
|
+
messageCount: number;
|
|
35
|
+
pageType?: string | undefined;
|
|
36
|
+
sku?: string | undefined;
|
|
37
|
+
sourceSessionId: string;
|
|
38
|
+
}
|
|
39
|
+
export interface ChatHistorySessionRecord extends ChatHistoryIndexEntry {
|
|
40
|
+
version: number;
|
|
41
|
+
userId: string;
|
|
42
|
+
appId: string;
|
|
43
|
+
messages: StoredHistoryMessage[];
|
|
44
|
+
currentThreadId: string | null;
|
|
45
|
+
lastThreadId: string | null;
|
|
46
|
+
panelThreads?: string[] | undefined;
|
|
47
|
+
/** Legacy thumbnail-strip data kept optional for backward compatibility with older local history. */
|
|
48
|
+
thumbnailEntries?: LegacyThumbnailEntry[] | undefined;
|
|
49
|
+
panelSnapshotHtml?: Record<string, string> | undefined;
|
|
50
|
+
panelSnapshotTypes?: Record<string, string> | undefined;
|
|
51
|
+
panelAiSpecByThread?: Record<string, UISpec> | undefined;
|
|
52
|
+
lastBackendContext: BackendContext | null;
|
|
53
|
+
}
|
|
54
|
+
export interface SaveHistorySessionParams {
|
|
55
|
+
historyId: string;
|
|
56
|
+
userId: string;
|
|
57
|
+
appId: string;
|
|
58
|
+
sourceSessionId: string;
|
|
59
|
+
messages: ChatMessage[];
|
|
60
|
+
currentThreadId: string | null;
|
|
61
|
+
lastThreadId: string | null;
|
|
62
|
+
chatCreatedAt: string;
|
|
63
|
+
panelSnapshots: Map<string, HTMLElement>;
|
|
64
|
+
panelSnapshotTypes: Map<string, string>;
|
|
65
|
+
panelThreads: string[];
|
|
66
|
+
panelAiSpecByThread?: Map<string, UISpec> | undefined;
|
|
67
|
+
lastBackendContext: BackendContext | null;
|
|
68
|
+
pageType?: string | undefined;
|
|
69
|
+
sku?: string | undefined;
|
|
70
|
+
}
|
|
71
|
+
export declare class ChatHistoryStorage {
|
|
72
|
+
private readonly _appId;
|
|
73
|
+
private readonly _userId;
|
|
74
|
+
private readonly _storage;
|
|
75
|
+
private readonly _scope;
|
|
76
|
+
constructor(_appId: string, _userId: string, _storage?: Storage | null);
|
|
77
|
+
createHistoryId(): string;
|
|
78
|
+
findSessionId(sourceSessionId: string, createdAt: string): string | null;
|
|
79
|
+
listSessions(): ChatHistoryIndexEntry[];
|
|
80
|
+
loadSession(historyId: string): ChatHistorySessionRecord | null;
|
|
81
|
+
saveSession(params: SaveHistorySessionParams): ChatHistorySessionRecord | null;
|
|
82
|
+
deleteSession(historyId: string): void;
|
|
83
|
+
private _commitRecord;
|
|
84
|
+
}
|
|
85
|
+
export {};
|
package/dist/chat/index.d.ts
CHANGED
|
@@ -63,9 +63,11 @@ export declare class GengageChat extends BaseWidget<ChatWidgetConfig> {
|
|
|
63
63
|
private _comparisonSelectedSkus;
|
|
64
64
|
private _comparisonSelectionWarning;
|
|
65
65
|
private _comparisonRefreshRafId;
|
|
66
|
+
private _lastAppliedKeyboardInset;
|
|
66
67
|
/** SKUs of products the user has viewed across panel product grids. */
|
|
67
68
|
private _viewedProductSkus;
|
|
68
|
-
|
|
69
|
+
/** Latest AI analysis UISpec (AITopPicks/AIGroupingCards) per thread for panel restore. */
|
|
70
|
+
private _panelAiSpecByThread;
|
|
69
71
|
private _choicePrompterEl;
|
|
70
72
|
private _openState;
|
|
71
73
|
private _mobileBreakpoint;
|
|
@@ -113,6 +115,10 @@ export declare class GengageChat extends BaseWidget<ChatWidgetConfig> {
|
|
|
113
115
|
private _currentPanelSource;
|
|
114
116
|
/** IndexedDB session persistence manager. */
|
|
115
117
|
private _session;
|
|
118
|
+
/** LocalStorage-backed chat history manager. */
|
|
119
|
+
private _historyStorage;
|
|
120
|
+
/** Active local history session ID for the current conversation. */
|
|
121
|
+
private _activeHistorySessionId;
|
|
116
122
|
/** Transcript focus, pin-to-bottom, and scroll request coordination. */
|
|
117
123
|
private readonly _presentation;
|
|
118
124
|
/** Registered event callbacks (GA4 event hooks). Key = event name, value = set of callbacks. */
|
|
@@ -169,8 +175,12 @@ export declare class GengageChat extends BaseWidget<ChatWidgetConfig> {
|
|
|
169
175
|
* delay or distort the next response.
|
|
170
176
|
*/
|
|
171
177
|
private _pruneEmptyStreamingAssistantPlaceholders;
|
|
178
|
+
/** Clear all runtime conversation state while keeping the widget mounted and ready. */
|
|
179
|
+
private _clearConversationState;
|
|
172
180
|
/** Reset all chat state when navigating to a different SKU/page. */
|
|
173
181
|
private _resetForNewPage;
|
|
182
|
+
/** Start a brand-new local conversation on the current page context. */
|
|
183
|
+
private _startNewChat;
|
|
174
184
|
/**
|
|
175
185
|
* Same side effects as stream UISpec `clearPanel`: hide/clear the assistant panel without
|
|
176
186
|
* `restoreOrClearPanel()`. Used for `clearPanel` chunks and PDP chat layout (`productDetailsExtended` off).
|
|
@@ -262,9 +272,20 @@ export declare class GengageChat extends BaseWidget<ChatWidgetConfig> {
|
|
|
262
272
|
private _applyPanelListHeadingToContext;
|
|
263
273
|
private _renderPanelFromSource;
|
|
264
274
|
private _handleRollback;
|
|
275
|
+
private _ensureMobileFullSheetForPanel;
|
|
276
|
+
private _ensureMobilePanelOverlayVisible;
|
|
265
277
|
private _ensurePdpPrimeSuggestedUiIfNeeded;
|
|
266
278
|
/** Rewind the conversation to the given thread. */
|
|
267
279
|
private _rollbackToThread;
|
|
280
|
+
private _persistHistoryToLocalStorage;
|
|
281
|
+
private _persistConversationState;
|
|
282
|
+
private _persistConversationStateForNavigation;
|
|
283
|
+
private _formatHistoryTimestamp;
|
|
284
|
+
private _openHistoryPanel;
|
|
285
|
+
private _buildHistoryPageEl;
|
|
286
|
+
private _deleteHistorySession;
|
|
287
|
+
private _loadHistorySession;
|
|
288
|
+
private _restoreFromHistoryRecord;
|
|
268
289
|
private _persistToIndexedDB;
|
|
269
290
|
private _isSameOriginUrl;
|
|
270
291
|
private _markUnavailableProductContext;
|
|
@@ -289,8 +310,6 @@ export declare class GengageChat extends BaseWidget<ChatWidgetConfig> {
|
|
|
289
310
|
* then fall back to thread-level history.
|
|
290
311
|
*/
|
|
291
312
|
private _navigatePanelBack;
|
|
292
|
-
private _shouldUseDividerPreviewForSpec;
|
|
293
|
-
private _shouldUseDividerPreviewForSource;
|
|
294
313
|
private _toggleComparisonSku;
|
|
295
314
|
/**
|
|
296
315
|
* Refresh the panel DOM to reflect the current comparison state without
|
|
@@ -318,6 +337,15 @@ export declare class GengageChat extends BaseWidget<ChatWidgetConfig> {
|
|
|
318
337
|
private _toggleProductFavorite;
|
|
319
338
|
private _openFavoritesPanel;
|
|
320
339
|
private _buildFavoritesPageEl;
|
|
340
|
+
private _isMessageHostedUISpec;
|
|
341
|
+
private _isPanelAiSpec;
|
|
342
|
+
private _rememberPanelAiSpec;
|
|
343
|
+
private _restorePanelAiSpecMap;
|
|
344
|
+
private _hydrateRestoredUISpecMetadata;
|
|
345
|
+
private _renderMessageUISpec;
|
|
346
|
+
private _maybeAddPanelRestoreMessage;
|
|
347
|
+
private _restorePanelFromFrontendMessage;
|
|
348
|
+
private _restorePanelAiZoneForThread;
|
|
321
349
|
/**
|
|
322
350
|
* Run registered callbacks for a GA4 event.
|
|
323
351
|
* If any callback returns false or throws, handle the failure (e.g. show error for cart-add).
|
|
@@ -42,7 +42,7 @@ export declare class PanelManager {
|
|
|
42
42
|
* Also restores the panel topbar title for the snapshot's component type.
|
|
43
43
|
* Returns true if the snapshot was found and restored.
|
|
44
44
|
*/
|
|
45
|
-
restoreForMessage(messageId: string): boolean;
|
|
45
|
+
restoreForMessage(messageId: string, highlightMessageId?: string): boolean;
|
|
46
46
|
/**
|
|
47
47
|
* Send maximize-pdp / minify-pdp bridge messages with production-matching delays.
|
|
48
48
|
* Called by the extended mode manager when panel extension state changes.
|
|
@@ -2,7 +2,6 @@ import { GengageIndexedDB, FavoriteData } from '../common/indexed-db.js';
|
|
|
2
2
|
import { CommunicationBridge } from '../common/communication-bridge.js';
|
|
3
3
|
import { BackendContext, UISpec } from '../common/types.js';
|
|
4
4
|
import { ChatMessage } from './types.js';
|
|
5
|
-
import { ThumbnailEntry } from './components/ThumbnailsColumn.js';
|
|
6
5
|
export type { FavoriteData };
|
|
7
6
|
type NavigateFn = (url: string) => void;
|
|
8
7
|
export interface PersistSessionParams {
|
|
@@ -14,8 +13,9 @@ export interface PersistSessionParams {
|
|
|
14
13
|
lastThreadId: string | null;
|
|
15
14
|
chatCreatedAt: string;
|
|
16
15
|
panelSnapshots: Map<string, HTMLElement>;
|
|
16
|
+
panelSnapshotTypes?: Map<string, string> | undefined;
|
|
17
17
|
panelThreads: string[];
|
|
18
|
-
|
|
18
|
+
panelAiSpecByThread?: Map<string, UISpec> | undefined;
|
|
19
19
|
lastBackendContext: BackendContext | null;
|
|
20
20
|
sku?: string | undefined;
|
|
21
21
|
}
|
package/dist/chat/types.d.ts
CHANGED
|
@@ -71,7 +71,7 @@ export interface ChatWidgetConfig extends BaseWidgetConfig {
|
|
|
71
71
|
/**
|
|
72
72
|
* Panel display mode:
|
|
73
73
|
* - 'auto' : Panel appears/hides with content; user can toggle (default)
|
|
74
|
-
* - 'collapsed' : Panel starts collapsed;
|
|
74
|
+
* - 'collapsed' : Panel starts collapsed; fresh panel content reopens it
|
|
75
75
|
* - 'expanded' : Panel starts expanded (users can still collapse/expand)
|
|
76
76
|
*/
|
|
77
77
|
panelMode?: 'auto' | 'collapsed' | 'expanded';
|
|
@@ -239,6 +239,11 @@ export interface ChatI18n {
|
|
|
239
239
|
offlineMessage: string;
|
|
240
240
|
cartAriaLabel: string;
|
|
241
241
|
favoritesAriaLabel: string;
|
|
242
|
+
historyAriaLabel: string;
|
|
243
|
+
historyPageTitle: string;
|
|
244
|
+
emptyHistoryMessage: string;
|
|
245
|
+
historyDeleteLabel: string;
|
|
246
|
+
historyDeleteConfirmMessage: string;
|
|
242
247
|
showPanelAriaLabel: string;
|
|
243
248
|
addToFavoritesLabel: string;
|
|
244
249
|
customerReviewsTitle: string;
|
|
@@ -352,7 +357,7 @@ export interface ChatUISpecRenderContext {
|
|
|
352
357
|
hideProductDiscountBadge?: boolean | undefined;
|
|
353
358
|
hideUserReviews?: boolean | undefined;
|
|
354
359
|
hideStockStatus?: boolean | undefined;
|
|
355
|
-
i18n?: Pick<ChatI18n, 'productCtaLabel' | 'viewOnSiteLabel' | 'aiTopPicksTitle' | 'roleWinner' | 'roleBestValue' | 'roleBestAlternative' | 'viewDetails' | 'groundingReviewCta' | 'groundingReviewSubtitle' | 'variantsLabel' | 'sortRelated' | 'sortPriceAsc' | 'sortPriceDesc' | 'sortToolbarAriaLabel' | 'compareSelected' | 'compareMinHint' | 'comparisonSelectLabel' | 'comparisonSelectedLabel' | 'comparisonSelectCardHint' | 'panelTitleProductDetails' | 'panelTitleSimilarProducts' | 'panelTitleComparisonResults' | 'panelTitleCategories' | 'panelTitleSearchResults' | 'inStockLabel' | 'outOfStockLabel' | 'findSimilarLabel' | 'galleryPrevAriaLabel' | 'galleryNextAriaLabel' | 'beautyStylesPreparedTitle' | 'watchStylesPreparedTitle' | 'consultingOtherCompatibleProductsLabel' | 'consultingFallbackGroupLabel' | 'consultingFallbackStyleLabel' | 'consultingStyleLoadingDescription' | 'consultingStyleUnavailableDescription' | 'consultingStyleLoadingBadge' | 'consultingStyleUnavailableBadge' | 'viewMoreLabel' | 'similarProductsLabel' | 'addToCartButton' | 'shareButton' | 'productInfoTab' | 'specificationsTab' | 'recommendedChoiceLabel' | 'highlightsLabel' | 'keyDifferencesLabel' | 'specialCasesLabel' | 'emptyReviewsMessage' | 'closeAriaLabel' | 'dismissAriaLabel' | 'startChatLabel' | 'handoffHeading' | 'customerReviewsTitle' | 'addToFavoritesLabel' | 'reviewFilterPositive' | 'reviewFilterNegative' | 'decreaseLabel' | 'increaseLabel' | 'reviewCustomersMentionSingular' | 'reviewCustomersMentionPlural' | 'reviewSubjectsHeading' | 'aiBrowseCategoriesTitle' | 'photoAnalysisBadge' | 'photoAnalysisStrengthsLabel' | 'photoAnalysisFocusLabel' | 'photoAnalysisCelebStyleLabel' | 'beautyPhotoStepTitle' | 'beautyPhotoStepDescription' | 'beautyPhotoStepUpload' | 'beautyPhotoStepProcessing' | 'beautyPhotoStepSkip'>;
|
|
360
|
+
i18n?: Pick<ChatI18n, 'productCtaLabel' | 'viewOnSiteLabel' | 'aiTopPicksTitle' | 'roleWinner' | 'roleBestValue' | 'roleBestAlternative' | 'viewDetails' | 'groundingReviewCta' | 'groundingReviewSubtitle' | 'variantsLabel' | 'sortRelated' | 'sortPriceAsc' | 'sortPriceDesc' | 'sortToolbarAriaLabel' | 'compareSelected' | 'compareMinHint' | 'comparisonSelectLabel' | 'comparisonSelectedLabel' | 'comparisonSelectCardHint' | 'panelTitleProductDetails' | 'panelTitleSimilarProducts' | 'panelTitleComparisonResults' | 'panelTitleCategories' | 'panelTitleSearchResults' | 'inStockLabel' | 'outOfStockLabel' | 'findSimilarLabel' | 'galleryPrevAriaLabel' | 'galleryNextAriaLabel' | 'beautyStylesPreparedTitle' | 'watchStylesPreparedTitle' | 'consultingOtherCompatibleProductsLabel' | 'consultingFallbackGroupLabel' | 'consultingFallbackStyleLabel' | 'consultingStyleLoadingDescription' | 'consultingStyleUnavailableDescription' | 'consultingStyleLoadingBadge' | 'consultingStyleUnavailableBadge' | 'viewMoreLabel' | 'similarProductsLabel' | 'addToCartButton' | 'shareButton' | 'productInfoTab' | 'specificationsTab' | 'recommendedChoiceLabel' | 'highlightsLabel' | 'keyDifferencesLabel' | 'specialCasesLabel' | 'emptyReviewsMessage' | 'closeAriaLabel' | 'dismissAriaLabel' | 'startChatLabel' | 'handoffHeading' | 'customerReviewsTitle' | 'addToFavoritesLabel' | 'showPanelAriaLabel' | 'reviewFilterPositive' | 'reviewFilterNegative' | 'decreaseLabel' | 'increaseLabel' | 'reviewCustomersMentionSingular' | 'reviewCustomersMentionPlural' | 'reviewSubjectsHeading' | 'aiBrowseCategoriesTitle' | 'photoAnalysisBadge' | 'photoAnalysisStrengthsLabel' | 'photoAnalysisFocusLabel' | 'photoAnalysisCelebStyleLabel' | 'beautyPhotoStepTitle' | 'beautyPhotoStepDescription' | 'beautyPhotoStepUpload' | 'beautyPhotoStepProcessing' | 'beautyPhotoStepSkip'>;
|
|
356
361
|
productSort?: ProductSortState | undefined;
|
|
357
362
|
onSortChange?: ((sort: ProductSortState) => void) | undefined;
|
|
358
363
|
comparisonSelectMode?: boolean | undefined;
|
|
@@ -384,6 +389,8 @@ export interface ChatMessage {
|
|
|
384
389
|
content?: string;
|
|
385
390
|
/** json-render UI spec attached to this message (e.g. product cards). */
|
|
386
391
|
uiSpec?: import('../common/types.js').UISpec;
|
|
392
|
+
/** Frontend-synthesized visible message; exclude from backend chat history. */
|
|
393
|
+
frontendOnly?: boolean;
|
|
387
394
|
/** Image attachment (user-uploaded). Stored in-memory until send. */
|
|
388
395
|
attachment?: File;
|
|
389
396
|
/** Snapshot of panel DOM at time this message's stream completed. */
|
|
@@ -420,6 +427,7 @@ export interface SerializableChatMessage {
|
|
|
420
427
|
threadId?: string | undefined;
|
|
421
428
|
role: 'user' | 'assistant';
|
|
422
429
|
content?: string | undefined;
|
|
430
|
+
frontendOnly?: boolean | undefined;
|
|
423
431
|
silent?: boolean | undefined;
|
|
424
432
|
timestamp: number;
|
|
425
433
|
status: 'streaming' | 'done' | 'error';
|