@thoughtspot/visual-embed-sdk 1.48.0 → 1.49.0
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/cjs/package.json +1 -1
- package/cjs/src/css-variables.d.ts +140 -0
- package/cjs/src/css-variables.d.ts.map +1 -1
- package/cjs/src/embed/app.d.ts +62 -1
- package/cjs/src/embed/app.d.ts.map +1 -1
- package/cjs/src/embed/app.js +57 -6
- package/cjs/src/embed/app.js.map +1 -1
- package/cjs/src/embed/app.spec.js +191 -1
- package/cjs/src/embed/app.spec.js.map +1 -1
- package/cjs/src/embed/auto-frame-renderer.js +7 -2
- package/cjs/src/embed/auto-frame-renderer.js.map +1 -1
- package/cjs/src/embed/auto-frame-renderer.spec.js +385 -6
- package/cjs/src/embed/auto-frame-renderer.spec.js.map +1 -1
- package/cjs/src/embed/base.d.ts +1 -0
- package/cjs/src/embed/base.d.ts.map +1 -1
- package/cjs/src/embed/base.js +13 -1
- package/cjs/src/embed/base.js.map +1 -1
- package/cjs/src/embed/base.spec.js +21 -0
- package/cjs/src/embed/base.spec.js.map +1 -1
- package/cjs/src/embed/bodyless-conversation.spec.js +86 -0
- package/cjs/src/embed/bodyless-conversation.spec.js.map +1 -1
- package/cjs/src/embed/conversation.d.ts +16 -1
- package/cjs/src/embed/conversation.d.ts.map +1 -1
- package/cjs/src/embed/conversation.js +5 -1
- package/cjs/src/embed/conversation.js.map +1 -1
- package/cjs/src/embed/conversation.spec.js +26 -0
- package/cjs/src/embed/conversation.spec.js.map +1 -1
- package/cjs/src/embed/liveboard.d.ts +47 -1
- package/cjs/src/embed/liveboard.d.ts.map +1 -1
- package/cjs/src/embed/liveboard.js +47 -6
- package/cjs/src/embed/liveboard.js.map +1 -1
- package/cjs/src/embed/liveboard.spec.js +129 -1
- package/cjs/src/embed/liveboard.spec.js.map +1 -1
- package/cjs/src/embed/spotter-viz-utils.d.ts +85 -0
- package/cjs/src/embed/spotter-viz-utils.d.ts.map +1 -0
- package/cjs/src/embed/spotter-viz-utils.js +17 -0
- package/cjs/src/embed/spotter-viz-utils.js.map +1 -0
- package/cjs/src/embed/spotter-viz-utils.spec.d.ts +2 -0
- package/cjs/src/embed/spotter-viz-utils.spec.d.ts.map +1 -0
- package/cjs/src/embed/spotter-viz-utils.spec.js +31 -0
- package/cjs/src/embed/spotter-viz-utils.spec.js.map +1 -0
- package/cjs/src/embed/ts-embed.d.ts +58 -38
- package/cjs/src/embed/ts-embed.d.ts.map +1 -1
- package/cjs/src/embed/ts-embed.js +245 -149
- package/cjs/src/embed/ts-embed.js.map +1 -1
- package/cjs/src/embed/ts-embed.spec.js +369 -123
- package/cjs/src/embed/ts-embed.spec.js.map +1 -1
- package/cjs/src/index.d.ts +2 -1
- package/cjs/src/index.d.ts.map +1 -1
- package/cjs/src/index.js.map +1 -1
- package/cjs/src/react/index.d.ts.map +1 -1
- package/cjs/src/react/index.js +3 -0
- package/cjs/src/react/index.js.map +1 -1
- package/cjs/src/types.d.ts +267 -27
- package/cjs/src/types.d.ts.map +1 -1
- package/cjs/src/types.js +223 -19
- package/cjs/src/types.js.map +1 -1
- package/cjs/src/utils/authService/tokenizedAuthService.spec.js +6 -7
- package/cjs/src/utils/authService/tokenizedAuthService.spec.js.map +1 -1
- package/cjs/src/utils/logger.js +2 -1
- package/cjs/src/utils/logger.js.map +1 -1
- package/cjs/src/utils/logger.spec.d.ts +1 -0
- package/cjs/src/utils/logger.spec.d.ts.map +1 -1
- package/cjs/src/utils/logger.spec.js +10 -9
- package/cjs/src/utils/logger.spec.js.map +1 -1
- package/cjs/src/utils.d.ts +4 -1
- package/cjs/src/utils.d.ts.map +1 -1
- package/cjs/src/utils.js +107 -10
- package/cjs/src/utils.js.map +1 -1
- package/cjs/src/utils.spec.js +163 -4
- package/cjs/src/utils.spec.js.map +1 -1
- package/dist/{index-Ck-r09gt.js → index-_UGCSSDR.js} +1 -1
- package/dist/src/css-variables.d.ts +140 -0
- package/dist/src/css-variables.d.ts.map +1 -1
- package/dist/src/embed/app.d.ts +62 -1
- package/dist/src/embed/app.d.ts.map +1 -1
- package/dist/src/embed/base.d.ts +1 -0
- package/dist/src/embed/base.d.ts.map +1 -1
- package/dist/src/embed/conversation.d.ts +16 -1
- package/dist/src/embed/conversation.d.ts.map +1 -1
- package/dist/src/embed/liveboard.d.ts +47 -1
- package/dist/src/embed/liveboard.d.ts.map +1 -1
- package/dist/src/embed/spotter-viz-utils.d.ts +85 -0
- package/dist/src/embed/spotter-viz-utils.d.ts.map +1 -0
- package/dist/src/embed/spotter-viz-utils.spec.d.ts +2 -0
- package/dist/src/embed/spotter-viz-utils.spec.d.ts.map +1 -0
- package/dist/src/embed/ts-embed.d.ts +58 -38
- package/dist/src/embed/ts-embed.d.ts.map +1 -1
- package/dist/src/index.d.ts +2 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/react/index.d.ts.map +1 -1
- package/dist/src/types.d.ts +267 -27
- package/dist/src/types.d.ts.map +1 -1
- package/dist/src/utils/logger.spec.d.ts +1 -0
- package/dist/src/utils/logger.spec.d.ts.map +1 -1
- package/dist/src/utils.d.ts +4 -1
- package/dist/src/utils.d.ts.map +1 -1
- package/dist/tsembed-react.es.js +3708 -3226
- package/dist/tsembed-react.js +3358 -2876
- package/dist/tsembed.es.js +3713 -3229
- package/dist/tsembed.js +3708 -3224
- package/dist/visual-embed-sdk-react-full.d.ts +643 -63
- package/dist/visual-embed-sdk-react.d.ts +643 -63
- package/dist/visual-embed-sdk.d.ts +658 -65
- package/lib/package.json +1 -1
- package/lib/src/css-variables.d.ts +140 -0
- package/lib/src/css-variables.d.ts.map +1 -1
- package/lib/src/embed/app.d.ts +62 -1
- package/lib/src/embed/app.d.ts.map +1 -1
- package/lib/src/embed/app.js +58 -7
- package/lib/src/embed/app.js.map +1 -1
- package/lib/src/embed/app.spec.js +192 -2
- package/lib/src/embed/app.spec.js.map +1 -1
- package/lib/src/embed/auto-frame-renderer.js +7 -2
- package/lib/src/embed/auto-frame-renderer.js.map +1 -1
- package/lib/src/embed/auto-frame-renderer.spec.js +387 -8
- package/lib/src/embed/auto-frame-renderer.spec.js.map +1 -1
- package/lib/src/embed/base.d.ts +1 -0
- package/lib/src/embed/base.d.ts.map +1 -1
- package/lib/src/embed/base.js +11 -0
- package/lib/src/embed/base.js.map +1 -1
- package/lib/src/embed/base.spec.js +22 -1
- package/lib/src/embed/base.spec.js.map +1 -1
- package/lib/src/embed/bodyless-conversation.spec.js +86 -0
- package/lib/src/embed/bodyless-conversation.spec.js.map +1 -1
- package/lib/src/embed/conversation.d.ts +16 -1
- package/lib/src/embed/conversation.d.ts.map +1 -1
- package/lib/src/embed/conversation.js +5 -1
- package/lib/src/embed/conversation.js.map +1 -1
- package/lib/src/embed/conversation.spec.js +27 -1
- package/lib/src/embed/conversation.spec.js.map +1 -1
- package/lib/src/embed/liveboard.d.ts +47 -1
- package/lib/src/embed/liveboard.d.ts.map +1 -1
- package/lib/src/embed/liveboard.js +48 -7
- package/lib/src/embed/liveboard.js.map +1 -1
- package/lib/src/embed/liveboard.spec.js +129 -1
- package/lib/src/embed/liveboard.spec.js.map +1 -1
- package/lib/src/embed/spotter-viz-utils.d.ts +85 -0
- package/lib/src/embed/spotter-viz-utils.d.ts.map +1 -0
- package/lib/src/embed/spotter-viz-utils.js +13 -0
- package/lib/src/embed/spotter-viz-utils.js.map +1 -0
- package/lib/src/embed/spotter-viz-utils.spec.d.ts +2 -0
- package/lib/src/embed/spotter-viz-utils.spec.d.ts.map +1 -0
- package/lib/src/embed/spotter-viz-utils.spec.js +29 -0
- package/lib/src/embed/spotter-viz-utils.spec.js.map +1 -0
- package/lib/src/embed/ts-embed.d.ts +58 -38
- package/lib/src/embed/ts-embed.d.ts.map +1 -1
- package/lib/src/embed/ts-embed.js +248 -152
- package/lib/src/embed/ts-embed.js.map +1 -1
- package/lib/src/embed/ts-embed.spec.js +369 -123
- package/lib/src/embed/ts-embed.spec.js.map +1 -1
- package/lib/src/index.d.ts +2 -1
- package/lib/src/index.d.ts.map +1 -1
- package/lib/src/index.js.map +1 -1
- package/lib/src/react/index.d.ts.map +1 -1
- package/lib/src/react/index.js +3 -0
- package/lib/src/react/index.js.map +1 -1
- package/lib/src/types.d.ts +267 -27
- package/lib/src/types.d.ts.map +1 -1
- package/lib/src/types.js +223 -19
- package/lib/src/types.js.map +1 -1
- package/lib/src/utils/authService/tokenizedAuthService.spec.js +6 -7
- package/lib/src/utils/authService/tokenizedAuthService.spec.js.map +1 -1
- package/lib/src/utils/logger.js +2 -1
- package/lib/src/utils/logger.js.map +1 -1
- package/lib/src/utils/logger.spec.d.ts +1 -0
- package/lib/src/utils/logger.spec.d.ts.map +1 -1
- package/lib/src/utils/logger.spec.js +10 -9
- package/lib/src/utils/logger.spec.js.map +1 -1
- package/lib/src/utils.d.ts +4 -1
- package/lib/src/utils.d.ts.map +1 -1
- package/lib/src/utils.js +103 -9
- package/lib/src/utils.js.map +1 -1
- package/lib/src/utils.spec.js +164 -5
- package/lib/src/utils.spec.js.map +1 -1
- package/lib/src/visual-embed-sdk.d.ts +658 -65
- package/package.json +1 -1
- package/src/css-variables.ts +175 -1
- package/src/embed/app.spec.ts +247 -3
- package/src/embed/app.ts +125 -5
- package/src/embed/auto-frame-renderer.spec.ts +457 -58
- package/src/embed/auto-frame-renderer.ts +7 -2
- package/src/embed/base.spec.ts +25 -1
- package/src/embed/base.ts +19 -5
- package/src/embed/bodyless-conversation.spec.ts +93 -0
- package/src/embed/conversation.spec.ts +34 -0
- package/src/embed/conversation.ts +22 -1
- package/src/embed/liveboard.spec.ts +149 -1
- package/src/embed/liveboard.ts +102 -6
- package/src/embed/spotter-viz-utils.spec.ts +30 -0
- package/src/embed/spotter-viz-utils.ts +94 -0
- package/src/embed/ts-embed.spec.ts +532 -234
- package/src/embed/ts-embed.ts +383 -257
- package/src/index.ts +3 -0
- package/src/react/index.tsx +3 -0
- package/src/types.ts +284 -23
- package/src/utils/authService/tokenizedAuthService.spec.ts +6 -6
- package/src/utils/logger.spec.ts +11 -9
- package/src/utils/logger.ts +2 -2
- package/src/utils.spec.ts +200 -4
- package/src/utils.ts +128 -9
|
@@ -133,9 +133,9 @@ const getMockAppInitPayload = (data: any) => {
|
|
|
133
133
|
customVariablesForThirdPartyTools,
|
|
134
134
|
interceptTimeout: undefined,
|
|
135
135
|
interceptUrls: [],
|
|
136
|
-
shouldBypassPayloadValidation:undefined,
|
|
137
|
-
useHostEventsV2:undefined,
|
|
138
|
-
embedExpiryInAuthToken:true
|
|
136
|
+
shouldBypassPayloadValidation: undefined,
|
|
137
|
+
useHostEventsV2: undefined,
|
|
138
|
+
embedExpiryInAuthToken: true,
|
|
139
139
|
};
|
|
140
140
|
return {
|
|
141
141
|
type: EmbedEvent.APP_INIT,
|
|
@@ -144,7 +144,7 @@ const getMockAppInitPayload = (data: any) => {
|
|
|
144
144
|
...data,
|
|
145
145
|
},
|
|
146
146
|
};
|
|
147
|
-
}
|
|
147
|
+
};
|
|
148
148
|
|
|
149
149
|
describe('Unit test case for ts embed', () => {
|
|
150
150
|
const mockMixPanelEvent = jest.spyOn(mixpanelInstance, 'uploadMixpanelEvent');
|
|
@@ -223,9 +223,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
223
223
|
liveboardEmbed.render();
|
|
224
224
|
mockProcessTrigger.mockResolvedValue({ session: 'test' });
|
|
225
225
|
await executeAfterWait(async () => {
|
|
226
|
-
await liveboardEmbed.trigger(
|
|
227
|
-
HostEvent.Save,
|
|
228
|
-
);
|
|
226
|
+
await liveboardEmbed.trigger(HostEvent.Save);
|
|
229
227
|
expect(mockProcessTrigger).toHaveBeenCalledWith(
|
|
230
228
|
getIFrameEl(),
|
|
231
229
|
HostEvent.Save,
|
|
@@ -244,10 +242,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
244
242
|
liveboardEmbed.render();
|
|
245
243
|
mockProcessTrigger.mockResolvedValue({ session: 'test' });
|
|
246
244
|
await executeAfterWait(async () => {
|
|
247
|
-
await liveboardEmbed.trigger(
|
|
248
|
-
HostEvent.Save,
|
|
249
|
-
false,
|
|
250
|
-
);
|
|
245
|
+
await liveboardEmbed.trigger(HostEvent.Save, false);
|
|
251
246
|
expect(mockProcessTrigger).toHaveBeenCalledWith(
|
|
252
247
|
getIFrameEl(),
|
|
253
248
|
HostEvent.Save,
|
|
@@ -398,9 +393,11 @@ describe('Unit test case for ts embed', () => {
|
|
|
398
393
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
399
394
|
});
|
|
400
395
|
await executeAfterWait(() => {
|
|
401
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
402
|
-
|
|
403
|
-
|
|
396
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
397
|
+
getMockAppInitPayload({
|
|
398
|
+
customisations: customisationsView,
|
|
399
|
+
}),
|
|
400
|
+
);
|
|
404
401
|
});
|
|
405
402
|
});
|
|
406
403
|
|
|
@@ -427,9 +424,11 @@ describe('Unit test case for ts embed', () => {
|
|
|
427
424
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
428
425
|
});
|
|
429
426
|
await executeAfterWait(() => {
|
|
430
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
431
|
-
|
|
432
|
-
|
|
427
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
428
|
+
getMockAppInitPayload({
|
|
429
|
+
hiddenHomepageModules: [HomepageModule.MyLibrary, HomepageModule.Learning],
|
|
430
|
+
}),
|
|
431
|
+
);
|
|
433
432
|
});
|
|
434
433
|
});
|
|
435
434
|
|
|
@@ -480,10 +479,14 @@ describe('Unit test case for ts embed', () => {
|
|
|
480
479
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
481
480
|
});
|
|
482
481
|
await executeAfterWait(() => {
|
|
483
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
484
|
-
|
|
485
|
-
[
|
|
486
|
-
|
|
482
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
483
|
+
getMockAppInitPayload({
|
|
484
|
+
reorderedHomepageModules: [
|
|
485
|
+
HomepageModule.MyLibrary,
|
|
486
|
+
HomepageModule.Watchlist,
|
|
487
|
+
],
|
|
488
|
+
}),
|
|
489
|
+
);
|
|
487
490
|
});
|
|
488
491
|
});
|
|
489
492
|
|
|
@@ -513,9 +516,11 @@ describe('Unit test case for ts embed', () => {
|
|
|
513
516
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
514
517
|
});
|
|
515
518
|
await executeAfterWait(() => {
|
|
516
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
517
|
-
|
|
518
|
-
|
|
519
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
520
|
+
getMockAppInitPayload({
|
|
521
|
+
runtimeParameterParams: 'param1=color¶mVal1=blue',
|
|
522
|
+
}),
|
|
523
|
+
);
|
|
519
524
|
});
|
|
520
525
|
});
|
|
521
526
|
|
|
@@ -546,9 +551,11 @@ describe('Unit test case for ts embed', () => {
|
|
|
546
551
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
547
552
|
});
|
|
548
553
|
await executeAfterWait(() => {
|
|
549
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
550
|
-
|
|
551
|
-
|
|
554
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
555
|
+
getMockAppInitPayload({
|
|
556
|
+
runtimeFilterParams: 'col1=color&op1=EQ&val1=blue',
|
|
557
|
+
}),
|
|
558
|
+
);
|
|
552
559
|
});
|
|
553
560
|
});
|
|
554
561
|
|
|
@@ -638,10 +645,14 @@ describe('Unit test case for ts embed', () => {
|
|
|
638
645
|
});
|
|
639
646
|
|
|
640
647
|
await executeAfterWait(() => {
|
|
641
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
642
|
-
|
|
643
|
-
[
|
|
644
|
-
|
|
648
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
649
|
+
getMockAppInitPayload({
|
|
650
|
+
hiddenHomeLeftNavItems: [
|
|
651
|
+
HomeLeftNavItem.Home,
|
|
652
|
+
HomeLeftNavItem.MonitorSubscription,
|
|
653
|
+
],
|
|
654
|
+
}),
|
|
655
|
+
);
|
|
645
656
|
});
|
|
646
657
|
});
|
|
647
658
|
|
|
@@ -824,10 +835,12 @@ describe('Unit test case for ts embed', () => {
|
|
|
824
835
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
825
836
|
});
|
|
826
837
|
await executeAfterWait(() => {
|
|
827
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
838
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
839
|
+
getMockAppInitPayload({
|
|
840
|
+
authToken: 'test_auth_token1',
|
|
841
|
+
customVariablesForThirdPartyTools: {},
|
|
842
|
+
}),
|
|
843
|
+
);
|
|
831
844
|
});
|
|
832
845
|
|
|
833
846
|
jest.spyOn(authService, 'verifyTokenService').mockClear();
|
|
@@ -878,37 +891,40 @@ describe('Unit test case for ts embed', () => {
|
|
|
878
891
|
|
|
879
892
|
await executeAfterWait(() => {
|
|
880
893
|
const iframe = getIFrameEl();
|
|
881
|
-
expect(iframe.src).toContain(
|
|
894
|
+
expect(iframe.src).toContain(
|
|
895
|
+
'overrideStringIDsUrl=https://sample-string-ids-url.com',
|
|
896
|
+
);
|
|
882
897
|
postMessageToParent(iframe.contentWindow, mockEmbedEventPayload, mockPort);
|
|
883
898
|
});
|
|
884
899
|
|
|
885
900
|
await executeAfterWait(() => {
|
|
886
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
901
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
902
|
+
getMockAppInitPayload({
|
|
903
|
+
customisations: {
|
|
904
|
+
content: {
|
|
905
|
+
strings: {
|
|
906
|
+
Liveboard: 'Dashboard',
|
|
907
|
+
},
|
|
908
|
+
stringIDsUrl: 'https://sample-string-ids-url.com',
|
|
909
|
+
stringIDs: {
|
|
910
|
+
'liveboard.header.title': 'Dashboard name',
|
|
911
|
+
},
|
|
891
912
|
},
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
913
|
+
style: {
|
|
914
|
+
customCSS: {},
|
|
915
|
+
customCSSUrl: undefined,
|
|
895
916
|
},
|
|
896
917
|
},
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
.toBe('https://sample-string-ids-url.com');
|
|
908
|
-
expect(customisationContent.stringIDs)
|
|
909
|
-
.toEqual({
|
|
910
|
-
'liveboard.header.title': 'Dashboard name',
|
|
911
|
-
});
|
|
918
|
+
authToken: 'test_auth_token1',
|
|
919
|
+
customVariablesForThirdPartyTools: {},
|
|
920
|
+
}),
|
|
921
|
+
);
|
|
922
|
+
const customisationContent =
|
|
923
|
+
mockPort.postMessage.mock.calls[0][0].data.customisations.content;
|
|
924
|
+
expect(customisationContent.stringIDsUrl).toBe('https://sample-string-ids-url.com');
|
|
925
|
+
expect(customisationContent.stringIDs).toEqual({
|
|
926
|
+
'liveboard.header.title': 'Dashboard name',
|
|
927
|
+
});
|
|
912
928
|
});
|
|
913
929
|
});
|
|
914
930
|
|
|
@@ -917,7 +933,10 @@ describe('Unit test case for ts embed', () => {
|
|
|
917
933
|
type: EmbedEvent.APP_INIT,
|
|
918
934
|
data: {},
|
|
919
935
|
};
|
|
920
|
-
const searchEmbed = new SearchEmbed(getRootEl(), {
|
|
936
|
+
const searchEmbed = new SearchEmbed(getRootEl(), {
|
|
937
|
+
...defaultViewConfig,
|
|
938
|
+
exposeTranslationIDs: true,
|
|
939
|
+
});
|
|
921
940
|
searchEmbed.render();
|
|
922
941
|
const mockPort: any = {
|
|
923
942
|
postMessage: jest.fn(),
|
|
@@ -963,16 +982,16 @@ describe('Unit test case for ts embed', () => {
|
|
|
963
982
|
name: 'Valid Action',
|
|
964
983
|
target: CustomActionTarget.LIVEBOARD,
|
|
965
984
|
position: CustomActionsPosition.PRIMARY,
|
|
966
|
-
metadataIds: { liveboardIds: ['lb123'] }
|
|
985
|
+
metadataIds: { liveboardIds: ['lb123'] },
|
|
967
986
|
},
|
|
968
987
|
{
|
|
969
988
|
id: 'action2',
|
|
970
989
|
name: 'Another Valid Action',
|
|
971
990
|
target: CustomActionTarget.VIZ,
|
|
972
991
|
position: CustomActionsPosition.MENU,
|
|
973
|
-
metadataIds: { vizIds: ['viz456'] }
|
|
974
|
-
}
|
|
975
|
-
]
|
|
992
|
+
metadataIds: { vizIds: ['viz456'] },
|
|
993
|
+
},
|
|
994
|
+
],
|
|
976
995
|
});
|
|
977
996
|
|
|
978
997
|
searchEmbed.render();
|
|
@@ -986,33 +1005,35 @@ describe('Unit test case for ts embed', () => {
|
|
|
986
1005
|
});
|
|
987
1006
|
|
|
988
1007
|
await executeAfterWait(() => {
|
|
989
|
-
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
authToken: 'test_auth_token1',
|
|
998
|
-
customActions: [
|
|
999
|
-
{
|
|
1000
|
-
id: 'action2',
|
|
1001
|
-
name: 'Another Valid Action',
|
|
1002
|
-
target: CustomActionTarget.VIZ,
|
|
1003
|
-
position: CustomActionsPosition.MENU,
|
|
1004
|
-
metadataIds: { vizIds: ['viz456'] }
|
|
1008
|
+
expect(mockPort.postMessage).toHaveBeenCalledWith(
|
|
1009
|
+
getMockAppInitPayload({
|
|
1010
|
+
customisations: {
|
|
1011
|
+
content: {},
|
|
1012
|
+
style: {
|
|
1013
|
+
customCSS: {},
|
|
1014
|
+
customCSSUrl: undefined,
|
|
1015
|
+
},
|
|
1005
1016
|
},
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1017
|
+
authToken: 'test_auth_token1',
|
|
1018
|
+
customActions: [
|
|
1019
|
+
{
|
|
1020
|
+
id: 'action2',
|
|
1021
|
+
name: 'Another Valid Action',
|
|
1022
|
+
target: CustomActionTarget.VIZ,
|
|
1023
|
+
position: CustomActionsPosition.MENU,
|
|
1024
|
+
metadataIds: { vizIds: ['viz456'] },
|
|
1025
|
+
},
|
|
1026
|
+
{
|
|
1027
|
+
id: 'action1',
|
|
1028
|
+
name: 'Valid Action',
|
|
1029
|
+
target: CustomActionTarget.LIVEBOARD,
|
|
1030
|
+
position: CustomActionsPosition.PRIMARY,
|
|
1031
|
+
metadataIds: { liveboardIds: ['lb123'] },
|
|
1032
|
+
},
|
|
1033
|
+
], // Actions should be sorted by name
|
|
1034
|
+
customVariablesForThirdPartyTools: {},
|
|
1035
|
+
}),
|
|
1036
|
+
);
|
|
1016
1037
|
|
|
1017
1038
|
// Verify that CustomActionsValidationResult structure is
|
|
1018
1039
|
// correct
|
|
@@ -1024,15 +1045,15 @@ describe('Unit test case for ts embed', () => {
|
|
|
1024
1045
|
id: 'action1',
|
|
1025
1046
|
name: 'Valid Action',
|
|
1026
1047
|
target: CustomActionTarget.LIVEBOARD,
|
|
1027
|
-
position: CustomActionsPosition.PRIMARY
|
|
1048
|
+
position: CustomActionsPosition.PRIMARY,
|
|
1028
1049
|
}),
|
|
1029
1050
|
expect.objectContaining({
|
|
1030
1051
|
id: 'action2',
|
|
1031
1052
|
name: 'Another Valid Action',
|
|
1032
1053
|
target: CustomActionTarget.VIZ,
|
|
1033
|
-
position: CustomActionsPosition.MENU
|
|
1034
|
-
})
|
|
1035
|
-
])
|
|
1054
|
+
position: CustomActionsPosition.MENU,
|
|
1055
|
+
}),
|
|
1056
|
+
]),
|
|
1036
1057
|
);
|
|
1037
1058
|
|
|
1038
1059
|
// Verify actions are sorted by name (alphabetically)
|
|
@@ -1094,7 +1115,10 @@ describe('Unit test case for ts embed', () => {
|
|
|
1094
1115
|
type: EmbedEvent.APP_INIT,
|
|
1095
1116
|
data: {},
|
|
1096
1117
|
};
|
|
1097
|
-
const searchEmbed = new SearchEmbed(getRootEl(), {
|
|
1118
|
+
const searchEmbed = new SearchEmbed(getRootEl(), {
|
|
1119
|
+
...defaultViewConfig,
|
|
1120
|
+
preRenderId: 'test',
|
|
1121
|
+
});
|
|
1098
1122
|
searchEmbed.preRender();
|
|
1099
1123
|
const mockPort: any = {
|
|
1100
1124
|
postMessage: jest.fn(),
|
|
@@ -1153,7 +1177,10 @@ describe('Unit test case for ts embed', () => {
|
|
|
1153
1177
|
type: EmbedEvent.AuthExpire,
|
|
1154
1178
|
data: {},
|
|
1155
1179
|
};
|
|
1156
|
-
const searchEmbed = new SearchEmbed(getRootEl(), {
|
|
1180
|
+
const searchEmbed = new SearchEmbed(getRootEl(), {
|
|
1181
|
+
...defaultViewConfig,
|
|
1182
|
+
preRenderId: 'test',
|
|
1183
|
+
});
|
|
1157
1184
|
jest.spyOn(baseInstance, 'notifyAuthFailure');
|
|
1158
1185
|
searchEmbed.preRender();
|
|
1159
1186
|
const loggerSpy = jest.spyOn(logger, 'error').mockImplementation(() => {});
|
|
@@ -1318,23 +1345,27 @@ describe('Unit test case for ts embed', () => {
|
|
|
1318
1345
|
let mockGetPreauthInfo = null;
|
|
1319
1346
|
|
|
1320
1347
|
if (overrideOrgId) {
|
|
1321
|
-
mockGetPreauthInfo = jest
|
|
1348
|
+
mockGetPreauthInfo = jest
|
|
1349
|
+
.spyOn(sessionInfoService, 'getPreauthInfo')
|
|
1350
|
+
.mockImplementation(jest.fn());
|
|
1322
1351
|
}
|
|
1323
1352
|
|
|
1324
|
-
const mockPreauthInfoFetch = jest
|
|
1325
|
-
|
|
1326
|
-
|
|
1327
|
-
|
|
1328
|
-
|
|
1329
|
-
|
|
1330
|
-
|
|
1331
|
-
|
|
1353
|
+
const mockPreauthInfoFetch = jest
|
|
1354
|
+
.spyOn(authService, 'fetchPreauthInfoService')
|
|
1355
|
+
.mockResolvedValueOnce({
|
|
1356
|
+
ok: true,
|
|
1357
|
+
headers: new Headers({ 'content-type': 'application/json' }), // Mock headers correctly
|
|
1358
|
+
json: async () => ({
|
|
1359
|
+
info: {
|
|
1360
|
+
configInfo: {
|
|
1361
|
+
mixpanelConfig: {
|
|
1362
|
+
devSdkKey: 'devSdkKey',
|
|
1363
|
+
},
|
|
1332
1364
|
},
|
|
1365
|
+
userGUID: 'userGUID',
|
|
1333
1366
|
},
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
}), // Mock JSON response
|
|
1337
|
-
});
|
|
1367
|
+
}), // Mock JSON response
|
|
1368
|
+
});
|
|
1338
1369
|
const iFrame: any = document.createElement('div');
|
|
1339
1370
|
jest.spyOn(baseInstance, 'getAuthPromise').mockResolvedValueOnce(isLoggedIn);
|
|
1340
1371
|
const tsEmbed = new SearchEmbed(getRootEl(), {
|
|
@@ -1360,10 +1391,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
1360
1391
|
};
|
|
1361
1392
|
|
|
1362
1393
|
test('should call InfoSuccess Event on preauth call success', async () => {
|
|
1363
|
-
const {
|
|
1364
|
-
mockPreauthInfoFetch,
|
|
1365
|
-
iFrame,
|
|
1366
|
-
} = await setup(true);
|
|
1394
|
+
const { mockPreauthInfoFetch, iFrame } = await setup(true);
|
|
1367
1395
|
expect(mockPreauthInfoFetch).toHaveBeenCalledTimes(1);
|
|
1368
1396
|
|
|
1369
1397
|
await executeAfterWait(() => {
|
|
@@ -1378,9 +1406,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
1378
1406
|
});
|
|
1379
1407
|
|
|
1380
1408
|
test('should not call InfoSuccess Event if overrideOrgId is true', async () => {
|
|
1381
|
-
const {
|
|
1382
|
-
mockGetPreauthInfo,
|
|
1383
|
-
} = await setup(true, 123);
|
|
1409
|
+
const { mockGetPreauthInfo } = await setup(true, 123);
|
|
1384
1410
|
expect(mockGetPreauthInfo).toHaveBeenCalledTimes(0);
|
|
1385
1411
|
});
|
|
1386
1412
|
});
|
|
@@ -1405,7 +1431,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
1405
1431
|
embedType: 'AppEmbed' | 'SearchEmbed',
|
|
1406
1432
|
showPrimaryNavbar?: boolean,
|
|
1407
1433
|
overrideOrgId?: number,
|
|
1408
|
-
disablePreauthCache?: boolean
|
|
1434
|
+
disablePreauthCache?: boolean,
|
|
1409
1435
|
) => {
|
|
1410
1436
|
jest.spyOn(window, 'addEventListener').mockImplementationOnce(
|
|
1411
1437
|
(event, handler, options) => {
|
|
@@ -1422,18 +1448,23 @@ describe('Unit test case for ts embed', () => {
|
|
|
1422
1448
|
let mockGetPreauthInfo = null;
|
|
1423
1449
|
|
|
1424
1450
|
// Determine if preauth cache should be enabled
|
|
1425
|
-
const isAppEmbedWithPrimaryNavbar =
|
|
1426
|
-
|
|
1451
|
+
const isAppEmbedWithPrimaryNavbar =
|
|
1452
|
+
embedType === 'AppEmbed' && showPrimaryNavbar === true;
|
|
1453
|
+
const shouldDisableCache =
|
|
1454
|
+
overrideOrgId || disablePreauthCache || isAppEmbedWithPrimaryNavbar;
|
|
1427
1455
|
|
|
1428
1456
|
if (shouldDisableCache) {
|
|
1429
|
-
mockGetPreauthInfo = jest
|
|
1457
|
+
mockGetPreauthInfo = jest
|
|
1458
|
+
.spyOn(sessionInfoService, 'getPreauthInfo')
|
|
1430
1459
|
.mockImplementation(jest.fn());
|
|
1431
1460
|
} else {
|
|
1432
|
-
mockGetPreauthInfo = jest
|
|
1433
|
-
|
|
1461
|
+
mockGetPreauthInfo = jest
|
|
1462
|
+
.spyOn(sessionInfoService, 'getPreauthInfo')
|
|
1463
|
+
.mockResolvedValue({ info: { test: 'data' } } as any);
|
|
1434
1464
|
}
|
|
1435
1465
|
|
|
1436
|
-
const mockPreauthInfoFetch = jest
|
|
1466
|
+
const mockPreauthInfoFetch = jest
|
|
1467
|
+
.spyOn(authService, 'fetchPreauthInfoService')
|
|
1437
1468
|
.mockResolvedValueOnce({
|
|
1438
1469
|
ok: true,
|
|
1439
1470
|
headers: new Headers({ 'content-type': 'application/json' }),
|
|
@@ -1568,7 +1599,12 @@ describe('Unit test case for ts embed', () => {
|
|
|
1568
1599
|
});
|
|
1569
1600
|
|
|
1570
1601
|
test('should disable preauth cache for FullAppEmbed with disablePreauthCache = true', async () => {
|
|
1571
|
-
const { mockGetPreauthInfo } = await setupPreauthTest(
|
|
1602
|
+
const { mockGetPreauthInfo } = await setupPreauthTest(
|
|
1603
|
+
'AppEmbed',
|
|
1604
|
+
false,
|
|
1605
|
+
undefined,
|
|
1606
|
+
true,
|
|
1607
|
+
);
|
|
1572
1608
|
|
|
1573
1609
|
await executeAfterWait(() => {
|
|
1574
1610
|
expect(mockGetPreauthInfo).toHaveBeenCalledTimes(0);
|
|
@@ -1634,9 +1670,12 @@ describe('Unit test case for ts embed', () => {
|
|
|
1634
1670
|
|
|
1635
1671
|
test('mixpanel should call with VISUAL_SDK_RENDER_FAILED', () => {
|
|
1636
1672
|
expect(mockMixPanelEvent).toHaveBeenCalledWith(MIXPANEL_EVENT.VISUAL_SDK_RENDER_START);
|
|
1637
|
-
expect(mockMixPanelEvent).toHaveBeenCalledWith(
|
|
1638
|
-
|
|
1639
|
-
|
|
1673
|
+
expect(mockMixPanelEvent).toHaveBeenCalledWith(
|
|
1674
|
+
MIXPANEL_EVENT.VISUAL_SDK_RENDER_FAILED,
|
|
1675
|
+
{
|
|
1676
|
+
error: 'false',
|
|
1677
|
+
},
|
|
1678
|
+
);
|
|
1640
1679
|
});
|
|
1641
1680
|
});
|
|
1642
1681
|
|
|
@@ -2003,8 +2042,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
2003
2042
|
await appEmbed.render();
|
|
2004
2043
|
expectUrlMatchesWithParams(
|
|
2005
2044
|
getIFrameSrc(),
|
|
2006
|
-
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}`
|
|
2007
|
-
|
|
2045
|
+
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}` +
|
|
2046
|
+
`&foo=bar&baz=1&bool=true${defaultParamsPost}#/home`,
|
|
2008
2047
|
);
|
|
2009
2048
|
});
|
|
2010
2049
|
|
|
@@ -2032,8 +2071,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
2032
2071
|
await appEmbed.render();
|
|
2033
2072
|
expectUrlMatchesWithParams(
|
|
2034
2073
|
getIFrameSrc(),
|
|
2035
|
-
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}`
|
|
2036
|
-
|
|
2074
|
+
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}` +
|
|
2075
|
+
`&foo=bar&foo2=bar2&foo3=false&baz=1&bool=true${defaultParamsPost}#/home`,
|
|
2037
2076
|
);
|
|
2038
2077
|
});
|
|
2039
2078
|
|
|
@@ -2048,8 +2087,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
2048
2087
|
await appEmbed.render();
|
|
2049
2088
|
expectUrlMatchesWithParams(
|
|
2050
2089
|
getIFrameSrc(),
|
|
2051
|
-
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}`
|
|
2052
|
-
|
|
2090
|
+
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}` +
|
|
2091
|
+
`&showAlerts=true${defaultParamsPost}#/home`,
|
|
2053
2092
|
);
|
|
2054
2093
|
});
|
|
2055
2094
|
it('Sets the locale param', async () => {
|
|
@@ -2063,8 +2102,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
2063
2102
|
await appEmbed.render();
|
|
2064
2103
|
expectUrlMatchesWithParams(
|
|
2065
2104
|
getIFrameSrc(),
|
|
2066
|
-
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}`
|
|
2067
|
-
|
|
2105
|
+
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}` +
|
|
2106
|
+
`&locale=ja-JP${defaultParamsPost}#/home`,
|
|
2068
2107
|
);
|
|
2069
2108
|
});
|
|
2070
2109
|
it('Sets both params when enableLinkOverridesV2 is set', async () => {
|
|
@@ -2082,7 +2121,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
2082
2121
|
`http://${thoughtSpotHost}/?embedApp=true&${defaultParamsForPinboardEmbed}&enableLinkOverridesV2=true&linkOverride=true${defaultParamsPost}#/embed/viz/test-lb`,
|
|
2083
2122
|
);
|
|
2084
2123
|
});
|
|
2085
|
-
it('
|
|
2124
|
+
it('Auto-upgrades V1 linkOverride to V2 (sends both flags)', async () => {
|
|
2086
2125
|
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
2087
2126
|
frameParams: {
|
|
2088
2127
|
width: '100%',
|
|
@@ -2092,10 +2131,40 @@ describe('Unit test case for ts embed', () => {
|
|
|
2092
2131
|
linkOverride: true,
|
|
2093
2132
|
});
|
|
2094
2133
|
await liveboardEmbed.render();
|
|
2095
|
-
|
|
2096
|
-
|
|
2097
|
-
|
|
2098
|
-
|
|
2134
|
+
const src = getIFrameSrc();
|
|
2135
|
+
expect(src).toContain('linkOverride=true');
|
|
2136
|
+
expect(src).toContain('enableLinkOverridesV2=true');
|
|
2137
|
+
});
|
|
2138
|
+
it('Auto-disables V2 link overrides when disableRedirectionLinksInNewTab is true', async () => {
|
|
2139
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
2140
|
+
frameParams: {
|
|
2141
|
+
width: '100%',
|
|
2142
|
+
height: '100%',
|
|
2143
|
+
},
|
|
2144
|
+
liveboardId: 'test-lb',
|
|
2145
|
+
enableLinkOverridesV2: true,
|
|
2146
|
+
disableRedirectionLinksInNewTab: true,
|
|
2147
|
+
});
|
|
2148
|
+
await liveboardEmbed.render();
|
|
2149
|
+
const src = getIFrameSrc();
|
|
2150
|
+
expect(src).not.toContain('enableLinkOverridesV2=true');
|
|
2151
|
+
expect(src).not.toContain('linkOverride=true');
|
|
2152
|
+
expect(src).toContain('disableRedirectionLinksInNewTab=true');
|
|
2153
|
+
});
|
|
2154
|
+
it('Auto-disables V1 link override when disableRedirectionLinksInNewTab is true', async () => {
|
|
2155
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
2156
|
+
frameParams: {
|
|
2157
|
+
width: '100%',
|
|
2158
|
+
height: '100%',
|
|
2159
|
+
},
|
|
2160
|
+
liveboardId: 'test-lb',
|
|
2161
|
+
linkOverride: true,
|
|
2162
|
+
disableRedirectionLinksInNewTab: true,
|
|
2163
|
+
});
|
|
2164
|
+
await liveboardEmbed.render();
|
|
2165
|
+
const src = getIFrameSrc();
|
|
2166
|
+
expect(src).not.toContain('linkOverride=true');
|
|
2167
|
+
expect(src).toContain('disableRedirectionLinksInNewTab=true');
|
|
2099
2168
|
});
|
|
2100
2169
|
it('Sets the iconSprite url', async () => {
|
|
2101
2170
|
const appEmbed = new AppEmbed(getRootEl(), {
|
|
@@ -2110,8 +2179,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
2110
2179
|
await appEmbed.render();
|
|
2111
2180
|
expectUrlMatchesWithParams(
|
|
2112
2181
|
getIFrameSrc(),
|
|
2113
|
-
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}`
|
|
2114
|
-
|
|
2182
|
+
`http://${thoughtSpotHost}/?embedApp=true&primaryNavHidden=true&profileAndHelpInNavBarHidden=false&${defaultParamsForPinboardEmbed}` +
|
|
2183
|
+
`&iconSprite=iconSprite.com${defaultParamsPost}#/home`,
|
|
2115
2184
|
);
|
|
2116
2185
|
});
|
|
2117
2186
|
|
|
@@ -2391,8 +2460,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
2391
2460
|
tsEmbedDiv.style.height = '100px';
|
|
2392
2461
|
|
|
2393
2462
|
let resizeObserverCb: any;
|
|
2394
|
-
(window as any).ResizeObserver =
|
|
2395
|
-
|
|
2463
|
+
(window as any).ResizeObserver =
|
|
2464
|
+
window.ResizeObserver ||
|
|
2465
|
+
jest.fn().mockImplementation((resizeObserverCbParam) => {
|
|
2396
2466
|
resizeObserverCb = resizeObserverCbParam;
|
|
2397
2467
|
return {
|
|
2398
2468
|
disconnect: jest.fn(),
|
|
@@ -2406,9 +2476,12 @@ describe('Unit test case for ts embed', () => {
|
|
|
2406
2476
|
libEmbed.showPreRender();
|
|
2407
2477
|
expect(warnSpy).toHaveBeenCalledTimes(1);
|
|
2408
2478
|
|
|
2479
|
+
// The ResizeObserver now tracks the placeholder inside this.el,
|
|
2480
|
+
// not this.el itself, so pass it as the target.
|
|
2481
|
+
const preRenderPlaceholder = tsEmbedDiv.firstElementChild as HTMLElement;
|
|
2409
2482
|
resizeObserverCb([
|
|
2410
2483
|
{
|
|
2411
|
-
target:
|
|
2484
|
+
target: preRenderPlaceholder,
|
|
2412
2485
|
contentRect: { height: 297, width: 987 },
|
|
2413
2486
|
},
|
|
2414
2487
|
]);
|
|
@@ -2473,8 +2546,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
2473
2546
|
it('should set overflow:hidden when hidePreRender and remove when showPreRender', async () => {
|
|
2474
2547
|
createRootEleForEmbed();
|
|
2475
2548
|
|
|
2476
|
-
(window as any).ResizeObserver =
|
|
2477
|
-
|
|
2549
|
+
(window as any).ResizeObserver =
|
|
2550
|
+
window.ResizeObserver ||
|
|
2551
|
+
jest.fn().mockImplementation(() => ({
|
|
2478
2552
|
disconnect: jest.fn(),
|
|
2479
2553
|
observe: jest.fn(),
|
|
2480
2554
|
unobserve: jest.fn(),
|
|
@@ -2511,8 +2585,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
2511
2585
|
it('it should connect with another object', async () => {
|
|
2512
2586
|
createRootEleForEmbed();
|
|
2513
2587
|
mockMessageChannel();
|
|
2514
|
-
(window as any).ResizeObserver =
|
|
2515
|
-
|
|
2588
|
+
(window as any).ResizeObserver =
|
|
2589
|
+
window.ResizeObserver ||
|
|
2590
|
+
jest.fn().mockImplementation(() => ({
|
|
2516
2591
|
disconnect: jest.fn(),
|
|
2517
2592
|
observe: jest.fn(),
|
|
2518
2593
|
unobserve: jest.fn(),
|
|
@@ -2524,7 +2599,6 @@ describe('Unit test case for ts embed', () => {
|
|
|
2524
2599
|
|
|
2525
2600
|
libEmbed.preRender();
|
|
2526
2601
|
await waitFor(() => !!getIFrameEl());
|
|
2527
|
-
const warnSpy = jest.spyOn(logger, 'warn');
|
|
2528
2602
|
const newEmbed = new LiveboardEmbed('#tsEmbedDiv', {
|
|
2529
2603
|
preRenderId: 'i-am-preRendered',
|
|
2530
2604
|
liveboardId: 'awdawda',
|
|
@@ -2532,9 +2606,10 @@ describe('Unit test case for ts embed', () => {
|
|
|
2532
2606
|
frameParams: { height: 90 },
|
|
2533
2607
|
});
|
|
2534
2608
|
|
|
2535
|
-
newEmbed.showPreRender();
|
|
2609
|
+
await newEmbed.showPreRender();
|
|
2536
2610
|
|
|
2537
|
-
|
|
2611
|
+
// Verify newEmbed successfully connected to the existing preRender
|
|
2612
|
+
expect((newEmbed as any).isPreRenderConnected()).toBe(true);
|
|
2538
2613
|
});
|
|
2539
2614
|
it('showPreRender should not preRender if not available', async () => {
|
|
2540
2615
|
createRootEleForEmbed();
|
|
@@ -2711,7 +2786,10 @@ describe('Unit test case for ts embed', () => {
|
|
|
2711
2786
|
document.body.innerHTML = getDocumentBody();
|
|
2712
2787
|
});
|
|
2713
2788
|
test('Pre-render should wait for init to complete', async () => {
|
|
2714
|
-
const lib = new LiveboardEmbed(getRootEl(), {
|
|
2789
|
+
const lib = new LiveboardEmbed(getRootEl(), {
|
|
2790
|
+
preRenderId: 'test',
|
|
2791
|
+
liveboardId: 'test',
|
|
2792
|
+
});
|
|
2715
2793
|
lib.preRender();
|
|
2716
2794
|
await executeAfterWait(() => {
|
|
2717
2795
|
expect(errorSpy).toHaveBeenCalledWith(ERROR_MESSAGE.RENDER_CALLED_BEFORE_INIT);
|
|
@@ -2786,10 +2864,12 @@ describe('Unit test case for ts embed', () => {
|
|
|
2786
2864
|
jest.clearAllMocks();
|
|
2787
2865
|
document.body.innerHTML = getDocumentBody();
|
|
2788
2866
|
mockPort.postMessage.mockClear();
|
|
2789
|
-
jest.spyOn(authToken, 'getAuthenticationToken').mockResolvedValue(
|
|
2867
|
+
jest.spyOn(authToken, 'getAuthenticationToken').mockResolvedValue(
|
|
2868
|
+
'mock-test-token-placeholder',
|
|
2869
|
+
);
|
|
2790
2870
|
|
|
2791
2871
|
jest.spyOn(baseInstance, 'handleAuth').mockImplementation(() => Promise.resolve(true));
|
|
2792
|
-
jest.spyOn(baseInstance, 'notifyAuthFailure').mockImplementation(() => {
|
|
2872
|
+
jest.spyOn(baseInstance, 'notifyAuthFailure').mockImplementation(() => {});
|
|
2793
2873
|
});
|
|
2794
2874
|
|
|
2795
2875
|
const renderAndTriggerAuthExpire = async () => {
|
|
@@ -2902,7 +2982,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
2902
2982
|
|
|
2903
2983
|
afterEach(() => {
|
|
2904
2984
|
expect(baseInstance.notifyAuthFailure).toHaveBeenCalledWith(
|
|
2905
|
-
authInstance.AuthFailureType.EXPIRY
|
|
2985
|
+
authInstance.AuthFailureType.EXPIRY,
|
|
2906
2986
|
);
|
|
2907
2987
|
});
|
|
2908
2988
|
});
|
|
@@ -2915,8 +2995,10 @@ describe('Unit test case for ts embed', () => {
|
|
|
2915
2995
|
jest.clearAllMocks();
|
|
2916
2996
|
document.body.innerHTML = getDocumentBody();
|
|
2917
2997
|
mockPort.postMessage.mockClear();
|
|
2918
|
-
jest.spyOn(authToken, 'getAuthenticationToken').mockResolvedValue(
|
|
2919
|
-
|
|
2998
|
+
jest.spyOn(authToken, 'getAuthenticationToken').mockResolvedValue(
|
|
2999
|
+
'mock-test-token-placeholder',
|
|
3000
|
+
);
|
|
3001
|
+
jest.spyOn(processData, 'processAuthFailure').mockImplementation(() => ({}) as any);
|
|
2920
3002
|
jest.spyOn(logger, 'error').mockImplementation(() => {});
|
|
2921
3003
|
});
|
|
2922
3004
|
|
|
@@ -2946,7 +3028,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
2946
3028
|
await executeAfterWait(() => {
|
|
2947
3029
|
expect(authToken.getAuthenticationToken).toHaveBeenCalledWith(
|
|
2948
3030
|
expect.any(Object),
|
|
2949
|
-
true
|
|
3031
|
+
true,
|
|
2950
3032
|
);
|
|
2951
3033
|
});
|
|
2952
3034
|
});
|
|
@@ -2963,7 +3045,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
2963
3045
|
await executeAfterWait(() => {
|
|
2964
3046
|
expect(authToken.getAuthenticationToken).toHaveBeenCalledWith(
|
|
2965
3047
|
expect.any(Object),
|
|
2966
|
-
true
|
|
3048
|
+
true,
|
|
2967
3049
|
);
|
|
2968
3050
|
});
|
|
2969
3051
|
});
|
|
@@ -2998,17 +3080,19 @@ describe('Unit test case for ts embed', () => {
|
|
|
2998
3080
|
await executeAfterWait(() => {
|
|
2999
3081
|
expect(authToken.getAuthenticationToken).toHaveBeenCalledWith(
|
|
3000
3082
|
expect.any(Object),
|
|
3001
|
-
true
|
|
3083
|
+
true,
|
|
3002
3084
|
);
|
|
3003
3085
|
// Check that logger.error was called with the token refresh
|
|
3004
3086
|
// error
|
|
3005
3087
|
const errorCalls = (logger.error as jest.Mock).mock.calls.filter(
|
|
3006
|
-
(call) =>
|
|
3088
|
+
(call) =>
|
|
3089
|
+
call[0]?.includes(ERROR_MESSAGE.INVALID_TOKEN_ERROR) &&
|
|
3090
|
+
call[0]?.includes('Token fetch failed'),
|
|
3007
3091
|
);
|
|
3008
3092
|
expect(errorCalls.length).toBeGreaterThan(0);
|
|
3009
3093
|
expect(processData.processAuthFailure).toHaveBeenCalledWith(
|
|
3010
3094
|
error,
|
|
3011
|
-
expect.any(Element)
|
|
3095
|
+
expect.any(Element),
|
|
3012
3096
|
);
|
|
3013
3097
|
expect(mockPort.postMessage).not.toHaveBeenCalled();
|
|
3014
3098
|
});
|
|
@@ -3197,7 +3281,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
3197
3281
|
isEmbedContainerLoaded: true,
|
|
3198
3282
|
};
|
|
3199
3283
|
|
|
3200
|
-
jest.spyOn(searchEmbed as any, 'getPreRenderObj').mockReturnValue(
|
|
3284
|
+
jest.spyOn(searchEmbed as any, 'getPreRenderObj').mockReturnValue(
|
|
3285
|
+
mockPreRenderObj as any,
|
|
3286
|
+
);
|
|
3201
3287
|
|
|
3202
3288
|
const result = searchEmbed['checkEmbedContainerLoaded']();
|
|
3203
3289
|
|
|
@@ -3209,8 +3295,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3209
3295
|
const searchEmbed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
3210
3296
|
const loggerSpy = jest.spyOn(logger, 'info');
|
|
3211
3297
|
|
|
3212
|
-
//
|
|
3213
|
-
(searchEmbed as any).
|
|
3298
|
+
// getPreRenderObj reads the embed reference from preRenderWrapper
|
|
3299
|
+
(searchEmbed as any).preRenderWrapper = {
|
|
3214
3300
|
[searchEmbed['embedNodeKey']]: searchEmbed,
|
|
3215
3301
|
};
|
|
3216
3302
|
|
|
@@ -3273,7 +3359,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3273
3359
|
const searchEmbed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
3274
3360
|
searchEmbed.isEmbedContainerLoaded = true;
|
|
3275
3361
|
|
|
3276
|
-
const triggerSpy = jest
|
|
3362
|
+
const triggerSpy = jest
|
|
3363
|
+
.spyOn(searchEmbed, 'trigger')
|
|
3277
3364
|
.mockResolvedValue(mockContext);
|
|
3278
3365
|
|
|
3279
3366
|
const context = await searchEmbed.getCurrentContext();
|
|
@@ -3286,7 +3373,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3286
3373
|
const searchEmbed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
3287
3374
|
searchEmbed.isEmbedContainerLoaded = false;
|
|
3288
3375
|
|
|
3289
|
-
const triggerSpy = jest
|
|
3376
|
+
const triggerSpy = jest
|
|
3377
|
+
.spyOn(searchEmbed, 'trigger')
|
|
3290
3378
|
.mockResolvedValue(mockContext);
|
|
3291
3379
|
|
|
3292
3380
|
const contextPromise = searchEmbed.getCurrentContext();
|
|
@@ -3338,7 +3426,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
3338
3426
|
test('should handle handleEmbedContainerLoaded with EmbedListenerReady source', () => {
|
|
3339
3427
|
const searchEmbed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
3340
3428
|
|
|
3341
|
-
const handler = searchEmbed['createEmbedContainerHandler'](
|
|
3429
|
+
const handler = searchEmbed['createEmbedContainerHandler'](
|
|
3430
|
+
EmbedEvent.EmbedListenerReady,
|
|
3431
|
+
);
|
|
3342
3432
|
|
|
3343
3433
|
expect(searchEmbed.isEmbedContainerLoaded).toBe(false);
|
|
3344
3434
|
|
|
@@ -3408,7 +3498,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
3408
3498
|
new Error('Auth failed'),
|
|
3409
3499
|
);
|
|
3410
3500
|
const searchEmbed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
3411
|
-
const errorSpy = jest.spyOn(console, 'error').mockImplementation(() => {
|
|
3501
|
+
const errorSpy = jest.spyOn(console, 'error').mockImplementation(() => {});
|
|
3412
3502
|
await searchEmbed.render();
|
|
3413
3503
|
await executeAfterWait(() => {
|
|
3414
3504
|
expect(getRootEl().innerHTML).toContain('Not logged in');
|
|
@@ -3530,11 +3620,13 @@ describe('Unit test case for ts embed', () => {
|
|
|
3530
3620
|
await appEmbed.render();
|
|
3531
3621
|
|
|
3532
3622
|
jest.spyOn(appEmbed, 'trigger').mockRejectedValue(new Error('trigger failed'));
|
|
3533
|
-
const removeChildSpy = jest
|
|
3623
|
+
const removeChildSpy = jest
|
|
3624
|
+
.spyOn(Node.prototype, 'removeChild')
|
|
3625
|
+
.mockImplementation(() => getRootEl());
|
|
3534
3626
|
|
|
3535
3627
|
appEmbed.destroy();
|
|
3536
3628
|
|
|
3537
|
-
await new Promise(resolve => setTimeout(resolve, 50));
|
|
3629
|
+
await new Promise((resolve) => setTimeout(resolve, 50));
|
|
3538
3630
|
|
|
3539
3631
|
expect(removeChildSpy).toHaveBeenCalled();
|
|
3540
3632
|
|
|
@@ -3567,7 +3659,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
3567
3659
|
await appEmbed.render();
|
|
3568
3660
|
|
|
3569
3661
|
const triggerSpy = jest.spyOn(appEmbed, 'trigger').mockResolvedValue(null);
|
|
3570
|
-
const removeChildSpy = jest
|
|
3662
|
+
const removeChildSpy = jest
|
|
3663
|
+
.spyOn(Node.prototype, 'removeChild')
|
|
3664
|
+
.mockImplementation(() => getRootEl());
|
|
3571
3665
|
|
|
3572
3666
|
appEmbed.destroy();
|
|
3573
3667
|
|
|
@@ -3591,7 +3685,9 @@ describe('Unit test case for ts embed', () => {
|
|
|
3591
3685
|
await appEmbed.render();
|
|
3592
3686
|
|
|
3593
3687
|
const triggerSpy = jest.spyOn(appEmbed, 'trigger').mockResolvedValue(null);
|
|
3594
|
-
const removeChildSpy = jest
|
|
3688
|
+
const removeChildSpy = jest
|
|
3689
|
+
.spyOn(Node.prototype, 'removeChild')
|
|
3690
|
+
.mockImplementation(() => getRootEl());
|
|
3595
3691
|
|
|
3596
3692
|
appEmbed.destroy();
|
|
3597
3693
|
|
|
@@ -3599,7 +3695,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
3599
3695
|
expect(triggerSpy).toHaveBeenCalledWith(HostEvent.DestroyEmbed);
|
|
3600
3696
|
|
|
3601
3697
|
// Wait for the timeout to complete
|
|
3602
|
-
await new Promise(resolve => setTimeout(resolve, 1100));
|
|
3698
|
+
await new Promise((resolve) => setTimeout(resolve, 1100));
|
|
3603
3699
|
|
|
3604
3700
|
expect(removeChildSpy).toHaveBeenCalled();
|
|
3605
3701
|
});
|
|
@@ -3620,15 +3716,19 @@ describe('Unit test case for ts embed', () => {
|
|
|
3620
3716
|
await appEmbed.render();
|
|
3621
3717
|
|
|
3622
3718
|
// Mock trigger to resolve quickly (before timeout)
|
|
3623
|
-
const triggerSpy = jest
|
|
3624
|
-
|
|
3625
|
-
|
|
3626
|
-
|
|
3719
|
+
const triggerSpy = jest
|
|
3720
|
+
.spyOn(appEmbed, 'trigger')
|
|
3721
|
+
.mockImplementation(
|
|
3722
|
+
() => new Promise((resolve) => setTimeout(() => resolve(null), 100)),
|
|
3723
|
+
);
|
|
3724
|
+
const removeChildSpy = jest
|
|
3725
|
+
.spyOn(Node.prototype, 'removeChild')
|
|
3726
|
+
.mockImplementation(() => getRootEl());
|
|
3627
3727
|
|
|
3628
3728
|
appEmbed.destroy();
|
|
3629
3729
|
|
|
3630
3730
|
// Wait for the trigger to complete
|
|
3631
|
-
await new Promise(resolve => setTimeout(resolve, 200));
|
|
3731
|
+
await new Promise((resolve) => setTimeout(resolve, 200));
|
|
3632
3732
|
|
|
3633
3733
|
expect(triggerSpy).toHaveBeenCalledWith(HostEvent.DestroyEmbed);
|
|
3634
3734
|
expect(removeChildSpy).toHaveBeenCalled();
|
|
@@ -3650,15 +3750,19 @@ describe('Unit test case for ts embed', () => {
|
|
|
3650
3750
|
await appEmbed.render();
|
|
3651
3751
|
|
|
3652
3752
|
// Mock trigger to take longer than timeout
|
|
3653
|
-
const triggerSpy = jest
|
|
3654
|
-
|
|
3655
|
-
|
|
3656
|
-
|
|
3753
|
+
const triggerSpy = jest
|
|
3754
|
+
.spyOn(appEmbed, 'trigger')
|
|
3755
|
+
.mockImplementation(
|
|
3756
|
+
() => new Promise((resolve) => setTimeout(() => resolve(null), 500)),
|
|
3757
|
+
);
|
|
3758
|
+
const removeChildSpy = jest
|
|
3759
|
+
.spyOn(Node.prototype, 'removeChild')
|
|
3760
|
+
.mockImplementation(() => getRootEl());
|
|
3657
3761
|
|
|
3658
3762
|
appEmbed.destroy();
|
|
3659
3763
|
|
|
3660
3764
|
// Wait for the timeout to complete
|
|
3661
|
-
await new Promise(resolve => setTimeout(resolve, 200));
|
|
3765
|
+
await new Promise((resolve) => setTimeout(resolve, 200));
|
|
3662
3766
|
|
|
3663
3767
|
expect(triggerSpy).toHaveBeenCalledWith(HostEvent.DestroyEmbed);
|
|
3664
3768
|
expect(removeChildSpy).toHaveBeenCalled();
|
|
@@ -3690,11 +3794,11 @@ describe('Unit test case for ts embed', () => {
|
|
|
3690
3794
|
body: JSON.stringify({
|
|
3691
3795
|
variables: {
|
|
3692
3796
|
session: { sessionId: 'session-123' },
|
|
3693
|
-
contextBookId: 'viz-456'
|
|
3694
|
-
}
|
|
3695
|
-
})
|
|
3696
|
-
}
|
|
3697
|
-
})
|
|
3797
|
+
contextBookId: 'viz-456',
|
|
3798
|
+
},
|
|
3799
|
+
}),
|
|
3800
|
+
},
|
|
3801
|
+
}),
|
|
3698
3802
|
};
|
|
3699
3803
|
|
|
3700
3804
|
const mockPort: any = {
|
|
@@ -3731,8 +3835,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3731
3835
|
type: EmbedEvent.ApiIntercept,
|
|
3732
3836
|
data: JSON.stringify({
|
|
3733
3837
|
input: '/prism/?op=GetChartWithData',
|
|
3734
|
-
init: {}
|
|
3735
|
-
})
|
|
3838
|
+
init: {},
|
|
3839
|
+
}),
|
|
3736
3840
|
};
|
|
3737
3841
|
|
|
3738
3842
|
const mockPort: any = {
|
|
@@ -3773,8 +3877,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3773
3877
|
type: EmbedEvent.ApiIntercept,
|
|
3774
3878
|
data: JSON.stringify({
|
|
3775
3879
|
input: '/prism/?op=GetChartWithData',
|
|
3776
|
-
init: {}
|
|
3777
|
-
})
|
|
3880
|
+
init: {},
|
|
3881
|
+
}),
|
|
3778
3882
|
};
|
|
3779
3883
|
|
|
3780
3884
|
const mockPort: any = {
|
|
@@ -3796,7 +3900,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
3796
3900
|
// handleInterceptEvent
|
|
3797
3901
|
const result = await capturedGetUnsavedAnswerTml({
|
|
3798
3902
|
sessionId: 'session-123',
|
|
3799
|
-
vizId: 'viz-456'
|
|
3903
|
+
vizId: 'viz-456',
|
|
3800
3904
|
});
|
|
3801
3905
|
|
|
3802
3906
|
expect(mockProcessTrigger).toHaveBeenCalled();
|
|
@@ -3807,8 +3911,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3807
3911
|
type: 'getUnsavedAnswerTML',
|
|
3808
3912
|
parameters: {
|
|
3809
3913
|
sessionId: 'session-123',
|
|
3810
|
-
vizId: 'viz-456'
|
|
3811
|
-
}
|
|
3914
|
+
vizId: 'viz-456',
|
|
3915
|
+
},
|
|
3812
3916
|
});
|
|
3813
3917
|
expect(result).toEqual(mockTmlResponse);
|
|
3814
3918
|
});
|
|
@@ -3828,8 +3932,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3828
3932
|
type: EmbedEvent.ApiIntercept,
|
|
3829
3933
|
data: JSON.stringify({
|
|
3830
3934
|
input: '/api/test',
|
|
3831
|
-
init: {}
|
|
3832
|
-
})
|
|
3935
|
+
init: {},
|
|
3936
|
+
}),
|
|
3833
3937
|
};
|
|
3834
3938
|
|
|
3835
3939
|
const mockPort: any = {
|
|
@@ -3858,8 +3962,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3858
3962
|
type: EmbedEvent.ApiIntercept,
|
|
3859
3963
|
data: JSON.stringify({
|
|
3860
3964
|
input: '/prism/?op=GetChartWithData',
|
|
3861
|
-
init: {}
|
|
3862
|
-
})
|
|
3965
|
+
init: {},
|
|
3966
|
+
}),
|
|
3863
3967
|
};
|
|
3864
3968
|
|
|
3865
3969
|
const mockPort: any = {
|
|
@@ -3911,16 +4015,16 @@ describe('Unit test case for ts embed', () => {
|
|
|
3911
4015
|
type: EmbedEvent.ApiIntercept,
|
|
3912
4016
|
data: JSON.stringify({
|
|
3913
4017
|
input: '/prism/?op=GetChartWithData',
|
|
3914
|
-
init: {}
|
|
3915
|
-
})
|
|
4018
|
+
init: {},
|
|
4019
|
+
}),
|
|
3916
4020
|
};
|
|
3917
4021
|
|
|
3918
4022
|
const mockEventData2 = {
|
|
3919
4023
|
type: EmbedEvent.ApiIntercept,
|
|
3920
4024
|
data: JSON.stringify({
|
|
3921
4025
|
input: '/prism/?op=LoadContextBook',
|
|
3922
|
-
init: {}
|
|
3923
|
-
})
|
|
4026
|
+
init: {},
|
|
4027
|
+
}),
|
|
3924
4028
|
};
|
|
3925
4029
|
|
|
3926
4030
|
const mockPort: any = {
|
|
@@ -3956,8 +4060,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3956
4060
|
type: EmbedEvent.ApiIntercept,
|
|
3957
4061
|
data: JSON.stringify({
|
|
3958
4062
|
input: '/prism/?op=GetChartWithData',
|
|
3959
|
-
init: {}
|
|
3960
|
-
})
|
|
4063
|
+
init: {},
|
|
4064
|
+
}),
|
|
3961
4065
|
};
|
|
3962
4066
|
|
|
3963
4067
|
const mockPort: any = {
|
|
@@ -3997,8 +4101,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
3997
4101
|
type: EmbedEvent.ApiIntercept,
|
|
3998
4102
|
data: JSON.stringify({
|
|
3999
4103
|
input: '/prism/?op=GetChartWithData',
|
|
4000
|
-
init: {}
|
|
4001
|
-
})
|
|
4104
|
+
init: {},
|
|
4105
|
+
}),
|
|
4002
4106
|
};
|
|
4003
4107
|
|
|
4004
4108
|
const mockPort: any = {
|
|
@@ -4015,7 +4119,7 @@ describe('Unit test case for ts embed', () => {
|
|
|
4015
4119
|
|
|
4016
4120
|
const result = await capturedGetUnsavedAnswerTml({
|
|
4017
4121
|
sessionId: 'session-123',
|
|
4018
|
-
vizId: 'viz-456'
|
|
4122
|
+
vizId: 'viz-456',
|
|
4019
4123
|
});
|
|
4020
4124
|
|
|
4021
4125
|
expect(result).toBeUndefined();
|
|
@@ -4033,8 +4137,8 @@ describe('Unit test case for ts embed', () => {
|
|
|
4033
4137
|
type: EmbedEvent.ApiIntercept,
|
|
4034
4138
|
data: JSON.stringify({
|
|
4035
4139
|
input: '/prism/?op=LoadContextBook',
|
|
4036
|
-
init: {}
|
|
4037
|
-
})
|
|
4140
|
+
init: {},
|
|
4141
|
+
}),
|
|
4038
4142
|
};
|
|
4039
4143
|
|
|
4040
4144
|
const mockPort: any = {
|
|
@@ -4051,14 +4155,13 @@ describe('Unit test case for ts embed', () => {
|
|
|
4051
4155
|
expect(mockHandleInterceptEvent).toHaveBeenCalledWith(
|
|
4052
4156
|
expect.objectContaining({
|
|
4053
4157
|
eventData: mockEventData,
|
|
4054
|
-
})
|
|
4158
|
+
}),
|
|
4055
4159
|
);
|
|
4056
4160
|
});
|
|
4057
4161
|
});
|
|
4058
4162
|
});
|
|
4059
4163
|
});
|
|
4060
4164
|
|
|
4061
|
-
|
|
4062
4165
|
describe('Additional Coverage Tests', () => {
|
|
4063
4166
|
beforeAll(() => {
|
|
4064
4167
|
init({
|
|
@@ -4163,9 +4266,7 @@ describe('Trigger method edge cases', () => {
|
|
|
4163
4266
|
});
|
|
4164
4267
|
|
|
4165
4268
|
test('should return null when trigger is called before iframe is ready', async () => {
|
|
4166
|
-
jest.spyOn(baseInstance, 'getAuthPromise').mockRejectedValueOnce(
|
|
4167
|
-
new Error('Auth failed'),
|
|
4168
|
-
);
|
|
4269
|
+
jest.spyOn(baseInstance, 'getAuthPromise').mockRejectedValueOnce(new Error('Auth failed'));
|
|
4169
4270
|
const searchEmbed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4170
4271
|
jest.spyOn(logger, 'debug');
|
|
4171
4272
|
await searchEmbed.render();
|
|
@@ -4333,12 +4434,16 @@ describe('Fullscreen change handler behavior', () => {
|
|
|
4333
4434
|
});
|
|
4334
4435
|
|
|
4335
4436
|
describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
4336
|
-
const setupPreRenderTest = async (
|
|
4437
|
+
const setupPreRenderTest = async (
|
|
4438
|
+
preRenderId: string,
|
|
4439
|
+
initialConfig: Partial<LiveboardViewConfig>,
|
|
4440
|
+
) => {
|
|
4337
4441
|
createRootEleForEmbed();
|
|
4338
4442
|
mockMessageChannel();
|
|
4339
4443
|
|
|
4340
|
-
(window as any).ResizeObserver =
|
|
4341
|
-
|
|
4444
|
+
(window as any).ResizeObserver =
|
|
4445
|
+
window.ResizeObserver ||
|
|
4446
|
+
jest.fn().mockImplementation(() => ({
|
|
4342
4447
|
disconnect: jest.fn(),
|
|
4343
4448
|
observe: jest.fn(),
|
|
4344
4449
|
unobserve: jest.fn(),
|
|
@@ -4548,7 +4653,8 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4548
4653
|
});
|
|
4549
4654
|
});
|
|
4550
4655
|
|
|
4551
|
-
// Matches the structure produced by createValidationError /
|
|
4656
|
+
// Matches the structure produced by createValidationError /
|
|
4657
|
+
// embedErrorDetails
|
|
4552
4658
|
const makeNestedValidationData = (message = 'invalid payload') => ({
|
|
4553
4659
|
type: EmbedEvent.Error,
|
|
4554
4660
|
data: {
|
|
@@ -4559,7 +4665,8 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4559
4665
|
},
|
|
4560
4666
|
});
|
|
4561
4667
|
|
|
4562
|
-
// Matches the flat structure where errorType sits at the top level of
|
|
4668
|
+
// Matches the flat structure where errorType sits at the top level of
|
|
4669
|
+
// data
|
|
4563
4670
|
const makeFlatValidationData = (message = 'invalid payload') => ({
|
|
4564
4671
|
errorType: EmbedErrorCodes.HOST_EVENT_VALIDATION,
|
|
4565
4672
|
message,
|
|
@@ -4594,12 +4701,13 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4594
4701
|
const embed = makeEmbed({ useHostEventsV2: true, shouldBypassPayloadValidation: true });
|
|
4595
4702
|
embed.on(EmbedEvent.Error, errorHandler);
|
|
4596
4703
|
|
|
4597
|
-
(embed as any).executeCallbacks(
|
|
4704
|
+
(embed as any).executeCallbacks(
|
|
4705
|
+
EmbedEvent.Error,
|
|
4706
|
+
makeNestedValidationData('nested error'),
|
|
4707
|
+
);
|
|
4598
4708
|
|
|
4599
4709
|
expect(errorHandler).not.toHaveBeenCalled();
|
|
4600
|
-
expect(logger.warn).toHaveBeenCalledWith(
|
|
4601
|
-
'Host Event Validation failed: nested error',
|
|
4602
|
-
);
|
|
4710
|
+
expect(logger.warn).toHaveBeenCalledWith('Host Event Validation failed: nested error');
|
|
4603
4711
|
});
|
|
4604
4712
|
|
|
4605
4713
|
test('skips Error event when errorType is resolved from data.errorType (flat format)', () => {
|
|
@@ -4615,7 +4723,10 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4615
4723
|
|
|
4616
4724
|
test('delivers Error event to handler when useHostEventsV2 is true and shouldBypassPayloadValidation is undefined', () => {
|
|
4617
4725
|
const errorHandler = jest.fn();
|
|
4618
|
-
const embed = makeEmbed({
|
|
4726
|
+
const embed = makeEmbed({
|
|
4727
|
+
useHostEventsV2: true,
|
|
4728
|
+
shouldBypassPayloadValidation: undefined,
|
|
4729
|
+
});
|
|
4619
4730
|
embed.on(EmbedEvent.Error, errorHandler);
|
|
4620
4731
|
|
|
4621
4732
|
(embed as any).executeCallbacks(EmbedEvent.Error, makeNestedValidationData());
|
|
@@ -4625,7 +4736,10 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4625
4736
|
|
|
4626
4737
|
test('delivers Error event to handler when useHostEventsV2 is true and shouldBypassPayloadValidation is false', () => {
|
|
4627
4738
|
const errorHandler = jest.fn();
|
|
4628
|
-
const embed = makeEmbed({
|
|
4739
|
+
const embed = makeEmbed({
|
|
4740
|
+
useHostEventsV2: true,
|
|
4741
|
+
shouldBypassPayloadValidation: false,
|
|
4742
|
+
});
|
|
4629
4743
|
embed.on(EmbedEvent.Error, errorHandler);
|
|
4630
4744
|
|
|
4631
4745
|
(embed as any).executeCallbacks(EmbedEvent.Error, makeNestedValidationData());
|
|
@@ -4636,7 +4750,10 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4636
4750
|
test('skips Error event when useHostEventsV2 is false regardless of shouldBypassPayloadValidation', () => {
|
|
4637
4751
|
jest.spyOn(logger, 'warn');
|
|
4638
4752
|
const errorHandler = jest.fn();
|
|
4639
|
-
const embed = makeEmbed({
|
|
4753
|
+
const embed = makeEmbed({
|
|
4754
|
+
useHostEventsV2: false,
|
|
4755
|
+
shouldBypassPayloadValidation: undefined,
|
|
4756
|
+
});
|
|
4640
4757
|
embed.on(EmbedEvent.Error, errorHandler);
|
|
4641
4758
|
|
|
4642
4759
|
(embed as any).executeCallbacks(EmbedEvent.Error, makeNestedValidationData());
|
|
@@ -4660,13 +4777,18 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4660
4777
|
test('skips Error event when useHostEventsV2 is false and shouldBypassPayloadValidation is true', () => {
|
|
4661
4778
|
jest.spyOn(logger, 'warn');
|
|
4662
4779
|
const errorHandler = jest.fn();
|
|
4663
|
-
const embed = makeEmbed({
|
|
4780
|
+
const embed = makeEmbed({
|
|
4781
|
+
useHostEventsV2: false,
|
|
4782
|
+
shouldBypassPayloadValidation: true,
|
|
4783
|
+
});
|
|
4664
4784
|
embed.on(EmbedEvent.Error, errorHandler);
|
|
4665
4785
|
|
|
4666
4786
|
(embed as any).executeCallbacks(EmbedEvent.Error, makeNestedValidationData());
|
|
4667
4787
|
|
|
4668
4788
|
expect(errorHandler).not.toHaveBeenCalled();
|
|
4669
|
-
expect(logger.warn).toHaveBeenCalledWith(
|
|
4789
|
+
expect(logger.warn).toHaveBeenCalledWith(
|
|
4790
|
+
'Host Event Validation failed: invalid payload',
|
|
4791
|
+
);
|
|
4670
4792
|
});
|
|
4671
4793
|
|
|
4672
4794
|
test('skips via handleError when shouldBypassPayloadValidation is true', () => {
|
|
@@ -4691,7 +4813,10 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4691
4813
|
|
|
4692
4814
|
test('delivers Error event to EmbedEvent.ALL handler when not skipped', () => {
|
|
4693
4815
|
const allHandler = jest.fn();
|
|
4694
|
-
const embed = makeEmbed({
|
|
4816
|
+
const embed = makeEmbed({
|
|
4817
|
+
useHostEventsV2: true,
|
|
4818
|
+
shouldBypassPayloadValidation: false,
|
|
4819
|
+
});
|
|
4695
4820
|
embed.on(EmbedEvent.ALL, allHandler);
|
|
4696
4821
|
|
|
4697
4822
|
(embed as any).executeCallbacks(EmbedEvent.Error, makeNestedValidationData());
|
|
@@ -4701,7 +4826,10 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4701
4826
|
|
|
4702
4827
|
test('does not skip non-Error events even with HOST_EVENT_VALIDATION error code', () => {
|
|
4703
4828
|
const customActionHandler = jest.fn();
|
|
4704
|
-
const embed = makeEmbed({
|
|
4829
|
+
const embed = makeEmbed({
|
|
4830
|
+
useHostEventsV2: true,
|
|
4831
|
+
shouldBypassPayloadValidation: false,
|
|
4832
|
+
});
|
|
4705
4833
|
embed.on(EmbedEvent.CustomAction, customActionHandler);
|
|
4706
4834
|
|
|
4707
4835
|
(embed as any).executeCallbacks(EmbedEvent.CustomAction, {
|
|
@@ -4713,7 +4841,10 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4713
4841
|
|
|
4714
4842
|
test('does not skip Error events with unrelated error codes', () => {
|
|
4715
4843
|
const errorHandler = jest.fn();
|
|
4716
|
-
const embed = makeEmbed({
|
|
4844
|
+
const embed = makeEmbed({
|
|
4845
|
+
useHostEventsV2: true,
|
|
4846
|
+
shouldBypassPayloadValidation: false,
|
|
4847
|
+
});
|
|
4717
4848
|
embed.on(EmbedEvent.Error, errorHandler);
|
|
4718
4849
|
|
|
4719
4850
|
(embed as any).executeCallbacks(EmbedEvent.Error, {
|
|
@@ -4724,4 +4855,171 @@ describe('ShowPreRender with UpdateEmbedParams', () => {
|
|
|
4724
4855
|
expect(errorHandler).toHaveBeenCalled();
|
|
4725
4856
|
});
|
|
4726
4857
|
});
|
|
4858
|
+
|
|
4859
|
+
describe('constructor init-path branching (SCAL-315058)', () => {
|
|
4860
|
+
beforeEach(() => {
|
|
4861
|
+
init({
|
|
4862
|
+
thoughtSpotHost: 'tshost',
|
|
4863
|
+
authType: AuthType.None,
|
|
4864
|
+
});
|
|
4865
|
+
});
|
|
4866
|
+
|
|
4867
|
+
it('sets hostElement from domSelector', () => {
|
|
4868
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4869
|
+
expect((embed as any).hostElement).toBe(getRootEl());
|
|
4870
|
+
});
|
|
4871
|
+
|
|
4872
|
+
it('skips isReadyForRenderPromise when init already completed', () => {
|
|
4873
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(true);
|
|
4874
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4875
|
+
expect((embed as any).shouldWaitForRenderPromise).toBe(false);
|
|
4876
|
+
expect((embed as any).isReadyForRenderPromise).toBeUndefined();
|
|
4877
|
+
});
|
|
4878
|
+
|
|
4879
|
+
it('sets isReadyForRenderPromise when init not yet completed', () => {
|
|
4880
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(false);
|
|
4881
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4882
|
+
expect((embed as any).shouldWaitForRenderPromise).toBe(true);
|
|
4883
|
+
expect((embed as any).isReadyForRenderPromise).toBeInstanceOf(Promise);
|
|
4884
|
+
});
|
|
4885
|
+
|
|
4886
|
+
it('afterInit runs synchronously when init already completed', () => {
|
|
4887
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(true);
|
|
4888
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4889
|
+
// thoughtSpotHost is set by afterInit;
|
|
4890
|
+
// must be non-empty after constructor
|
|
4891
|
+
expect((embed as any).thoughtSpotHost).toBeTruthy();
|
|
4892
|
+
});
|
|
4893
|
+
|
|
4894
|
+
it('does not set isReadyForRenderPromise when shouldWaitForRenderPromise is false', () => {
|
|
4895
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(true);
|
|
4896
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4897
|
+
expect((embed as any).shouldWaitForRenderPromise).toBe(false);
|
|
4898
|
+
// isReadyForRenderPromise must be undefined
|
|
4899
|
+
// so no unnecessary await occurs
|
|
4900
|
+
expect((embed as any).isReadyForRenderPromise).toBeUndefined();
|
|
4901
|
+
});
|
|
4902
|
+
|
|
4903
|
+
it('shouldWaitForRenderPromise flips to false after promise settles', async () => {
|
|
4904
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(false);
|
|
4905
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4906
|
+
expect((embed as any).shouldWaitForRenderPromise).toBe(true);
|
|
4907
|
+
await (embed as any).isReadyForRenderPromise;
|
|
4908
|
+
expect((embed as any).shouldWaitForRenderPromise).toBe(false);
|
|
4909
|
+
});
|
|
4910
|
+
|
|
4911
|
+
it('calls throwInitError when getInitPromise rejects', async () => {
|
|
4912
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(false);
|
|
4913
|
+
jest.spyOn(baseInstance, 'getInitPromise').mockReturnValue(
|
|
4914
|
+
Promise.reject(new Error('init failed')),
|
|
4915
|
+
);
|
|
4916
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4917
|
+
const throwInitErrorSpy = jest.spyOn(embed as any, 'throwInitError');
|
|
4918
|
+
await (embed as any).isReadyForRenderPromise;
|
|
4919
|
+
expect(throwInitErrorSpy).toHaveBeenCalled();
|
|
4920
|
+
});
|
|
4921
|
+
|
|
4922
|
+
it('shouldWaitForRenderPromise flips to false even when getInitPromise rejects', async () => {
|
|
4923
|
+
jest.spyOn(baseInstance, 'getIsInitCompleted').mockReturnValue(false);
|
|
4924
|
+
jest.spyOn(baseInstance, 'getInitPromise').mockReturnValue(
|
|
4925
|
+
Promise.reject(new Error('init failed')),
|
|
4926
|
+
);
|
|
4927
|
+
const embed = new SearchEmbed(getRootEl(), defaultViewConfig);
|
|
4928
|
+
await (embed as any).isReadyForRenderPromise;
|
|
4929
|
+
expect((embed as any).shouldWaitForRenderPromise).toBe(false);
|
|
4930
|
+
});
|
|
4931
|
+
});
|
|
4932
|
+
|
|
4933
|
+
describe('preRender ID object includes placeHolder (SCAL-315058)', () => {
|
|
4934
|
+
beforeAll(() => {
|
|
4935
|
+
init({
|
|
4936
|
+
thoughtSpotHost: 'tshost',
|
|
4937
|
+
authType: AuthType.None,
|
|
4938
|
+
});
|
|
4939
|
+
});
|
|
4940
|
+
|
|
4941
|
+
it('getPreRenderIds returns placeHolder key', () => {
|
|
4942
|
+
createRootEleForEmbed();
|
|
4943
|
+
const embed = new LiveboardEmbed('#tsEmbedDiv', {
|
|
4944
|
+
preRenderId: 'ph-test',
|
|
4945
|
+
liveboardId: 'lb-id',
|
|
4946
|
+
});
|
|
4947
|
+
const ids = embed.getPreRenderIds();
|
|
4948
|
+
expect(ids.placeHolder).toBe('tsEmbed-pre-render-placeholder-ph-test');
|
|
4949
|
+
});
|
|
4950
|
+
});
|
|
4951
|
+
|
|
4952
|
+
describe('isPreRenderConnected logic (SCAL-315058)', () => {
|
|
4953
|
+
beforeAll(() => {
|
|
4954
|
+
init({
|
|
4955
|
+
thoughtSpotHost: 'tshost',
|
|
4956
|
+
authType: AuthType.None,
|
|
4957
|
+
});
|
|
4958
|
+
});
|
|
4959
|
+
|
|
4960
|
+
it('returns false when preRenderWrapper is absent', () => {
|
|
4961
|
+
createRootEleForEmbed();
|
|
4962
|
+
const embed = new LiveboardEmbed('#tsEmbedDiv', {
|
|
4963
|
+
preRenderId: 'conn-test',
|
|
4964
|
+
liveboardId: 'lb-id',
|
|
4965
|
+
});
|
|
4966
|
+
expect((embed as any).isPreRenderConnected()).toBe(false);
|
|
4967
|
+
});
|
|
4968
|
+
|
|
4969
|
+
it('returns true once preRenderWrapper and preRenderChild are set', () => {
|
|
4970
|
+
createRootEleForEmbed();
|
|
4971
|
+
const embed = new LiveboardEmbed('#tsEmbedDiv', {
|
|
4972
|
+
preRenderId: 'conn-test-2',
|
|
4973
|
+
liveboardId: 'lb-id',
|
|
4974
|
+
});
|
|
4975
|
+
(embed as any).preRenderWrapper = document.createElement('div');
|
|
4976
|
+
(embed as any).preRenderChild = document.createElement('div');
|
|
4977
|
+
expect((embed as any).isPreRenderConnected()).toBe(true);
|
|
4978
|
+
});
|
|
4979
|
+
});
|
|
4980
|
+
|
|
4981
|
+
describe('showPreRender inserts placeholder into hostElement (SCAL-315058)', () => {
|
|
4982
|
+
beforeAll(() => {
|
|
4983
|
+
// Clear spy implementations that may have leaked from prior
|
|
4984
|
+
// describe blocks (e.g. getIsInitCompleted/getInitPromise mocks set
|
|
4985
|
+
// in 'constructor init-path branching' persist across describes
|
|
4986
|
+
// because clearAllMocks only clears call history, not
|
|
4987
|
+
// implementations).
|
|
4988
|
+
jest.restoreAllMocks();
|
|
4989
|
+
jest.spyOn(authInstance, 'postLoginService').mockResolvedValue(undefined);
|
|
4990
|
+
init({
|
|
4991
|
+
thoughtSpotHost: 'tshost',
|
|
4992
|
+
authType: AuthType.None,
|
|
4993
|
+
});
|
|
4994
|
+
(window as any).ResizeObserver = jest.fn().mockImplementation(() => ({
|
|
4995
|
+
disconnect: jest.fn(),
|
|
4996
|
+
observe: jest.fn(),
|
|
4997
|
+
unobserve: jest.fn(),
|
|
4998
|
+
}));
|
|
4999
|
+
});
|
|
5000
|
+
|
|
5001
|
+
it('showPreRender creates a placeholder element with the correct id', async () => {
|
|
5002
|
+
createRootEleForEmbed();
|
|
5003
|
+
const embed = new LiveboardEmbed('#tsEmbedDiv', {
|
|
5004
|
+
preRenderId: 'ph-lifecycle-test',
|
|
5005
|
+
liveboardId: 'lb-id',
|
|
5006
|
+
});
|
|
5007
|
+
await embed.preRender();
|
|
5008
|
+
await waitFor(
|
|
5009
|
+
() => !!document.querySelector('#tsEmbed-pre-render-child-ph-lifecycle-test'),
|
|
5010
|
+
);
|
|
5011
|
+
|
|
5012
|
+
await embed.showPreRender();
|
|
5013
|
+
|
|
5014
|
+
const placeholderEle = (
|
|
5015
|
+
embed as any
|
|
5016
|
+
).getPreRenderPlaceHolderElement() as HTMLDivElement;
|
|
5017
|
+
expect(placeholderEle).not.toBeNull();
|
|
5018
|
+
expect(placeholderEle.id).toBe('tsEmbed-pre-render-placeholder-ph-lifecycle-test');
|
|
5019
|
+
// placeholder is attached to a parent element (inside hostElement)
|
|
5020
|
+
expect(placeholderEle.parentElement).not.toBeNull();
|
|
5021
|
+
|
|
5022
|
+
embed.destroy();
|
|
5023
|
+
});
|
|
5024
|
+
});
|
|
4727
5025
|
});
|