@thoughtspot/visual-embed-sdk 1.40.1-alpha.1 → 1.41.0-pre-render-1
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 +5 -4
- package/cjs/src/css-variables.d.ts +316 -0
- package/cjs/src/css-variables.d.ts.map +1 -1
- package/cjs/src/embed/app.d.ts.map +1 -1
- package/cjs/src/embed/app.js +8 -0
- package/cjs/src/embed/app.js.map +1 -1
- package/cjs/src/embed/app.spec.js +12 -2
- package/cjs/src/embed/app.spec.js.map +1 -1
- package/cjs/src/embed/bodyless-conversation.d.ts +1 -0
- package/cjs/src/embed/bodyless-conversation.d.ts.map +1 -1
- package/cjs/src/embed/bodyless-conversation.js +7 -3
- package/cjs/src/embed/bodyless-conversation.js.map +1 -1
- package/cjs/src/embed/conversation.d.ts +64 -2
- package/cjs/src/embed/conversation.d.ts.map +1 -1
- package/cjs/src/embed/conversation.js +16 -3
- package/cjs/src/embed/conversation.js.map +1 -1
- package/cjs/src/embed/conversation.spec.js +102 -0
- package/cjs/src/embed/conversation.spec.js.map +1 -1
- package/cjs/src/embed/liveboard.d.ts +12 -2
- package/cjs/src/embed/liveboard.d.ts.map +1 -1
- package/cjs/src/embed/liveboard.js +48 -18
- package/cjs/src/embed/liveboard.js.map +1 -1
- package/cjs/src/embed/liveboard.spec.js +211 -5
- package/cjs/src/embed/liveboard.spec.js.map +1 -1
- package/cjs/src/embed/sage.d.ts +1 -0
- package/cjs/src/embed/sage.d.ts.map +1 -1
- package/cjs/src/embed/sage.js +10 -6
- package/cjs/src/embed/sage.js.map +1 -1
- package/cjs/src/embed/search-bar.d.ts +1 -0
- package/cjs/src/embed/search-bar.d.ts.map +1 -1
- package/cjs/src/embed/search-bar.js +11 -7
- package/cjs/src/embed/search-bar.js.map +1 -1
- package/cjs/src/embed/search.d.ts +1 -0
- package/cjs/src/embed/search.d.ts.map +1 -1
- package/cjs/src/embed/search.js +7 -8
- package/cjs/src/embed/search.js.map +1 -1
- package/cjs/src/embed/ts-embed.d.ts +24 -7
- package/cjs/src/embed/ts-embed.d.ts.map +1 -1
- package/cjs/src/embed/ts-embed.js +87 -57
- package/cjs/src/embed/ts-embed.js.map +1 -1
- package/cjs/src/embed/ts-embed.spec.js +173 -1
- package/cjs/src/embed/ts-embed.spec.js.map +1 -1
- package/cjs/src/types.d.ts +152 -44
- package/cjs/src/types.d.ts.map +1 -1
- package/cjs/src/types.js +139 -42
- package/cjs/src/types.js.map +1 -1
- package/cjs/src/utils/liveboardService/liveboardService.d.ts +21 -6
- package/cjs/src/utils/liveboardService/liveboardService.d.ts.map +1 -1
- package/cjs/src/utils/liveboardService/liveboardService.js +21 -6
- package/cjs/src/utils/liveboardService/liveboardService.js.map +1 -1
- package/dist/index-BDlM0f0T.js +7371 -0
- package/dist/index-k7pkZMhx.js +7371 -0
- package/dist/src/css-variables.d.ts +316 -0
- package/dist/src/css-variables.d.ts.map +1 -1
- package/dist/src/embed/app.d.ts.map +1 -1
- package/dist/src/embed/bodyless-conversation.d.ts +5 -0
- package/dist/src/embed/bodyless-conversation.d.ts.map +1 -1
- package/dist/src/embed/conversation.d.ts +64 -2
- package/dist/src/embed/conversation.d.ts.map +1 -1
- package/dist/src/embed/liveboard.d.ts +11 -0
- package/dist/src/embed/liveboard.d.ts.map +1 -1
- package/dist/src/embed/sage.d.ts +1 -0
- package/dist/src/embed/sage.d.ts.map +1 -1
- package/dist/src/embed/search-bar.d.ts +1 -0
- package/dist/src/embed/search-bar.d.ts.map +1 -1
- package/dist/src/embed/search.d.ts +1 -0
- package/dist/src/embed/search.d.ts.map +1 -1
- package/dist/src/embed/ts-embed.d.ts +24 -0
- package/dist/src/embed/ts-embed.d.ts.map +1 -1
- package/dist/src/react/index.d.ts +2 -0
- package/dist/src/react/index.d.ts.map +1 -1
- package/dist/src/types.d.ts +351 -30
- package/dist/src/types.d.ts.map +1 -1
- package/dist/src/utils/graphql/nlsService/conversation-service.d.ts.map +1 -1
- package/dist/src/utils/liveboardService/liveboardService.d.ts +21 -6
- package/dist/src/utils/liveboardService/liveboardService.d.ts.map +1 -1
- package/dist/tsembed-react.es.js +551 -80
- package/dist/tsembed-react.js +550 -79
- package/dist/tsembed.es.js +572 -86
- package/dist/tsembed.js +571 -85
- package/dist/visual-embed-sdk-react-full.d.ts +787 -37
- package/dist/visual-embed-sdk-react.d.ts +787 -37
- package/dist/visual-embed-sdk.d.ts +785 -37
- package/lib/package.json +5 -4
- package/lib/src/css-variables.d.ts +316 -0
- package/lib/src/css-variables.d.ts.map +1 -1
- package/lib/src/embed/app.d.ts.map +1 -1
- package/lib/src/embed/app.js +8 -0
- package/lib/src/embed/app.js.map +1 -1
- package/lib/src/embed/app.spec.js +12 -2
- package/lib/src/embed/app.spec.js.map +1 -1
- package/lib/src/embed/bodyless-conversation.d.ts +1 -0
- package/lib/src/embed/bodyless-conversation.d.ts.map +1 -1
- package/lib/src/embed/bodyless-conversation.js +7 -3
- package/lib/src/embed/bodyless-conversation.js.map +1 -1
- package/lib/src/embed/conversation.d.ts +64 -2
- package/lib/src/embed/conversation.d.ts.map +1 -1
- package/lib/src/embed/conversation.js +17 -4
- package/lib/src/embed/conversation.js.map +1 -1
- package/lib/src/embed/conversation.spec.js +104 -2
- package/lib/src/embed/conversation.spec.js.map +1 -1
- package/lib/src/embed/liveboard.d.ts +12 -2
- package/lib/src/embed/liveboard.d.ts.map +1 -1
- package/lib/src/embed/liveboard.js +48 -18
- package/lib/src/embed/liveboard.js.map +1 -1
- package/lib/src/embed/liveboard.spec.js +211 -5
- package/lib/src/embed/liveboard.spec.js.map +1 -1
- package/lib/src/embed/sage.d.ts +1 -0
- package/lib/src/embed/sage.d.ts.map +1 -1
- package/lib/src/embed/sage.js +10 -6
- package/lib/src/embed/sage.js.map +1 -1
- package/lib/src/embed/search-bar.d.ts +1 -0
- package/lib/src/embed/search-bar.d.ts.map +1 -1
- package/lib/src/embed/search-bar.js +11 -7
- package/lib/src/embed/search-bar.js.map +1 -1
- package/lib/src/embed/search.d.ts +1 -0
- package/lib/src/embed/search.d.ts.map +1 -1
- package/lib/src/embed/search.js +7 -8
- package/lib/src/embed/search.js.map +1 -1
- package/lib/src/embed/ts-embed.d.ts +24 -7
- package/lib/src/embed/ts-embed.d.ts.map +1 -1
- package/lib/src/embed/ts-embed.js +87 -57
- package/lib/src/embed/ts-embed.js.map +1 -1
- package/lib/src/embed/ts-embed.spec.js +173 -1
- package/lib/src/embed/ts-embed.spec.js.map +1 -1
- package/lib/src/types.d.ts +152 -44
- package/lib/src/types.d.ts.map +1 -1
- package/lib/src/types.js +139 -42
- package/lib/src/types.js.map +1 -1
- package/lib/src/utils/liveboardService/liveboardService.d.ts +21 -6
- package/lib/src/utils/liveboardService/liveboardService.d.ts.map +1 -1
- package/lib/src/utils/liveboardService/liveboardService.js +21 -6
- package/lib/src/utils/liveboardService/liveboardService.js.map +1 -1
- package/lib/src/visual-embed-sdk.d.ts +786 -38
- package/package.json +6 -4
- package/src/css-variables.ts +396 -1
- package/src/embed/app.spec.ts +17 -2
- package/src/embed/app.ts +8 -0
- package/src/embed/bodyless-conversation.ts +8 -3
- package/src/embed/conversation.spec.ts +131 -5
- package/src/embed/conversation.ts +102 -12
- package/src/embed/liveboard.spec.ts +264 -5
- package/src/embed/liveboard.ts +55 -20
- package/src/embed/sage.ts +12 -7
- package/src/embed/search-bar.tsx +14 -7
- package/src/embed/search.ts +18 -7
- package/src/embed/ts-embed.spec.ts +345 -113
- package/src/embed/ts-embed.ts +97 -67
- package/src/types.ts +199 -91
- package/src/utils/liveboardService/liveboardService.ts +21 -6
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import isUndefined from 'lodash/isUndefined';
|
|
2
2
|
import { ERROR_MESSAGE } from '../errors';
|
|
3
|
-
import { Param, BaseViewConfig } from '../types';
|
|
3
|
+
import { Param, BaseViewConfig, RuntimeFilter, RuntimeParameter } from '../types';
|
|
4
4
|
import { TsEmbed } from './ts-embed';
|
|
5
|
-
import { getQueryParamString } from '../utils';
|
|
5
|
+
import { getQueryParamString, getFilterQuery, getRuntimeParameters } from '../utils';
|
|
6
6
|
|
|
7
|
-
/**
|
|
7
|
+
/**
|
|
8
8
|
* Configuration for search options
|
|
9
9
|
*/
|
|
10
10
|
export interface SearchOptions {
|
|
@@ -20,7 +20,8 @@ export interface SearchOptions {
|
|
|
20
20
|
*/
|
|
21
21
|
export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAction'> {
|
|
22
22
|
/**
|
|
23
|
-
* The ID of the data source object. For example, Model, View, or Table. Spotter uses
|
|
23
|
+
* The ID of the data source object. For example, Model, View, or Table. Spotter uses
|
|
24
|
+
* this object to query data and generate Answers.
|
|
24
25
|
*/
|
|
25
26
|
worksheetId: string;
|
|
26
27
|
/**
|
|
@@ -30,7 +31,7 @@ export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAct
|
|
|
30
31
|
/**
|
|
31
32
|
* disableSourceSelection : Disables data source selection
|
|
32
33
|
* but still display the selected data source.
|
|
33
|
-
*
|
|
34
|
+
*
|
|
34
35
|
* Supported embed types: `SpotterEmbed`
|
|
35
36
|
* @example
|
|
36
37
|
* ```js
|
|
@@ -44,7 +45,7 @@ export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAct
|
|
|
44
45
|
disableSourceSelection?: boolean;
|
|
45
46
|
/**
|
|
46
47
|
* hideSourceSelection : Hide data source selection
|
|
47
|
-
*
|
|
48
|
+
*
|
|
48
49
|
* Supported embed types: `SpotterEmbed`
|
|
49
50
|
* @example
|
|
50
51
|
* ```js
|
|
@@ -58,7 +59,7 @@ export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAct
|
|
|
58
59
|
hideSourceSelection?: boolean;
|
|
59
60
|
/**
|
|
60
61
|
* Flag to control Data panel experience
|
|
61
|
-
*
|
|
62
|
+
*
|
|
62
63
|
* Supported embed types: `SageEmbed`, `AppEmbed`, `SearchBarEmbed`, `LiveboardEmbed`, `SearchEmbed`
|
|
63
64
|
* @default false
|
|
64
65
|
* @version SDK: 1.36.0 | ThoughtSpot Cloud: 10.4.0.cl
|
|
@@ -76,7 +77,7 @@ export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAct
|
|
|
76
77
|
* showSpotterLimitations : show limitation text
|
|
77
78
|
* of the spotter underneath the chat input.
|
|
78
79
|
* default is false.
|
|
79
|
-
*
|
|
80
|
+
*
|
|
80
81
|
* Supported embed types: `SpotterEmbed`
|
|
81
82
|
* @example
|
|
82
83
|
* ```js
|
|
@@ -91,7 +92,7 @@ export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAct
|
|
|
91
92
|
/**
|
|
92
93
|
* hideSampleQuestions : Hide sample questions on
|
|
93
94
|
* the initial screen of the conversation.
|
|
94
|
-
*
|
|
95
|
+
*
|
|
95
96
|
* Supported embed types: `SpotterEmbed`
|
|
96
97
|
* @example
|
|
97
98
|
* ```js
|
|
@@ -103,6 +104,66 @@ export interface SpotterEmbedViewConfig extends Omit<BaseViewConfig, 'primaryAct
|
|
|
103
104
|
* @version SDK: 1.36.0 | ThoughtSpot: 10.6.0.cl
|
|
104
105
|
*/
|
|
105
106
|
hideSampleQuestions?: boolean;
|
|
107
|
+
/**
|
|
108
|
+
* The list of runtime filters to apply to a search Answer,
|
|
109
|
+
* visualization, or Liveboard.
|
|
110
|
+
*
|
|
111
|
+
* Supported embed types: `SpotterEmbed`
|
|
112
|
+
* @example
|
|
113
|
+
* ```js
|
|
114
|
+
* const embed = new SpotterEmbed('#tsEmbed', {
|
|
115
|
+
* // other embed view config
|
|
116
|
+
* runtimeFilters: [
|
|
117
|
+
* {
|
|
118
|
+
* columnName: 'color',
|
|
119
|
+
* operator: RuntimeFilterOp.EQ,
|
|
120
|
+
* values: ['red'],
|
|
121
|
+
* },
|
|
122
|
+
* ],
|
|
123
|
+
* })
|
|
124
|
+
* ```
|
|
125
|
+
* @version SDK: 1.41.0 | ThoughtSpot: 10.13.0.cl
|
|
126
|
+
*/
|
|
127
|
+
runtimeFilters?: RuntimeFilter[];
|
|
128
|
+
/**
|
|
129
|
+
* Flag to control whether runtime filters should be included in the URL.
|
|
130
|
+
* If true, filters will be passed via app initialization payload instead.
|
|
131
|
+
* If false/undefined, filters will be added to URL (default behavior).
|
|
132
|
+
*
|
|
133
|
+
* Supported embed types: `SpotterEmbed`
|
|
134
|
+
* @default false
|
|
135
|
+
* @version SDK: 1.41.0 | ThoughtSpot: 10.13.0.cl
|
|
136
|
+
*/
|
|
137
|
+
excludeRuntimeFiltersfromURL?: boolean;
|
|
138
|
+
/**
|
|
139
|
+
* The list of runtime parameters to apply to the conversation.
|
|
140
|
+
*
|
|
141
|
+
* Supported embed types: `SpotterEmbed`
|
|
142
|
+
* @example
|
|
143
|
+
* ```js
|
|
144
|
+
* const embed = new SpotterEmbed('#tsEmbed', {
|
|
145
|
+
* // other embed view config
|
|
146
|
+
* runtimeParameters: [
|
|
147
|
+
* {
|
|
148
|
+
* name: 'Integer Param',
|
|
149
|
+
* value: 10,
|
|
150
|
+
* },
|
|
151
|
+
* ],
|
|
152
|
+
* })
|
|
153
|
+
* ```
|
|
154
|
+
* @version SDK: 1.41.0 | ThoughtSpot: 10.13.0.cl
|
|
155
|
+
*/
|
|
156
|
+
runtimeParameters?: RuntimeParameter[];
|
|
157
|
+
/**
|
|
158
|
+
* Flag to control whether runtime parameters should be included in the URL.
|
|
159
|
+
* If true, parameters will be passed via app initialization payload instead.
|
|
160
|
+
* If false/undefined, parameters will be added to URL (default behavior).
|
|
161
|
+
*
|
|
162
|
+
* Supported embed types: `SpotterEmbed`
|
|
163
|
+
* @default false
|
|
164
|
+
* @version SDK: 1.41.0 | ThoughtSpot: 10.13.0.cl
|
|
165
|
+
*/
|
|
166
|
+
excludeRuntimeParametersfromURL?: boolean;
|
|
106
167
|
}
|
|
107
168
|
|
|
108
169
|
/**
|
|
@@ -135,7 +196,7 @@ export class SpotterEmbed extends TsEmbed {
|
|
|
135
196
|
super(container, viewConfig);
|
|
136
197
|
}
|
|
137
198
|
|
|
138
|
-
|
|
199
|
+
protected getEmbedParamsObject() {
|
|
139
200
|
const {
|
|
140
201
|
worksheetId,
|
|
141
202
|
searchOptions,
|
|
@@ -144,8 +205,12 @@ export class SpotterEmbed extends TsEmbed {
|
|
|
144
205
|
dataPanelV2,
|
|
145
206
|
showSpotterLimitations,
|
|
146
207
|
hideSampleQuestions,
|
|
208
|
+
runtimeFilters,
|
|
209
|
+
excludeRuntimeFiltersfromURL,
|
|
210
|
+
runtimeParameters,
|
|
211
|
+
excludeRuntimeParametersfromURL,
|
|
147
212
|
} = this.viewConfig;
|
|
148
|
-
|
|
213
|
+
|
|
149
214
|
if (!worksheetId) {
|
|
150
215
|
this.handleError(ERROR_MESSAGE.SPOTTER_EMBED_WORKSHEED_ID_NOT_FOUND);
|
|
151
216
|
}
|
|
@@ -170,16 +235,41 @@ export class SpotterEmbed extends TsEmbed {
|
|
|
170
235
|
queryParams[Param.HideSampleQuestions] = !!hideSampleQuestions;
|
|
171
236
|
}
|
|
172
237
|
|
|
238
|
+
return queryParams;
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
public getIframeSrc(): string {
|
|
242
|
+
const {
|
|
243
|
+
worksheetId,
|
|
244
|
+
searchOptions,
|
|
245
|
+
runtimeFilters,
|
|
246
|
+
excludeRuntimeFiltersfromURL,
|
|
247
|
+
runtimeParameters,
|
|
248
|
+
excludeRuntimeParametersfromURL,
|
|
249
|
+
} = this.viewConfig;
|
|
250
|
+
const path = 'insights/conv-assist';
|
|
251
|
+
const queryParams = this.getEmbedParamsObject();
|
|
252
|
+
|
|
173
253
|
let query = '';
|
|
174
254
|
const queryParamsString = getQueryParamString(queryParams, true);
|
|
175
255
|
if (queryParamsString) {
|
|
176
256
|
query = `?${queryParamsString}`;
|
|
177
257
|
}
|
|
258
|
+
|
|
259
|
+
const filterQuery = getFilterQuery(runtimeFilters || []);
|
|
260
|
+
if (filterQuery && !excludeRuntimeFiltersfromURL) {
|
|
261
|
+
query += `&${filterQuery}`;
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
const parameterQuery = getRuntimeParameters(runtimeParameters || []);
|
|
265
|
+
if (parameterQuery && !excludeRuntimeParametersfromURL) {
|
|
266
|
+
query += `&${parameterQuery}`;
|
|
267
|
+
}
|
|
268
|
+
|
|
178
269
|
const tsPostHashParams = this.getThoughtSpotPostUrlParams({
|
|
179
270
|
worksheet: worksheetId,
|
|
180
271
|
query: searchOptions?.searchQuery || '',
|
|
181
272
|
});
|
|
182
|
-
|
|
183
273
|
return `${this.getEmbedBasePath(query)}/embed/${path}${tsPostHashParams}`;
|
|
184
274
|
}
|
|
185
275
|
|
|
@@ -25,6 +25,7 @@ import * as tsEmbed from './ts-embed';
|
|
|
25
25
|
import * as processTriggerInstance from '../utils/processTrigger';
|
|
26
26
|
import * as auth from '../auth';
|
|
27
27
|
import * as previewService from '../utils/graphql/preview-service';
|
|
28
|
+
import * as SessionInfoService from '../utils/sessionInfoService';
|
|
28
29
|
|
|
29
30
|
const defaultViewConfig = {
|
|
30
31
|
frameParams: {
|
|
@@ -600,6 +601,14 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
600
601
|
|
|
601
602
|
test('navigateToLiveboard should trigger the navigate event with the correct path', async (done) => {
|
|
602
603
|
mockMessageChannel();
|
|
604
|
+
// mock getSessionInfo
|
|
605
|
+
jest.spyOn(SessionInfoService, 'getSessionInfo').mockResolvedValue({
|
|
606
|
+
releaseVersion: '1.0.0',
|
|
607
|
+
userGUID: '1234567890',
|
|
608
|
+
currentOrgId: 1,
|
|
609
|
+
privileges: [],
|
|
610
|
+
mixpanelToken: '1234567890',
|
|
611
|
+
});
|
|
603
612
|
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
604
613
|
...defaultViewConfig,
|
|
605
614
|
} as LiveboardViewConfig);
|
|
@@ -610,16 +619,30 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
610
619
|
postMessageToParent(iframe.contentWindow, {
|
|
611
620
|
type: EmbedEvent.APP_INIT,
|
|
612
621
|
});
|
|
622
|
+
postMessageToParent(iframe.contentWindow, {
|
|
623
|
+
type: EmbedEvent.AuthInit,
|
|
624
|
+
});
|
|
625
|
+
liveboardEmbed.navigateToLiveboard('lb1', 'viz1');
|
|
613
626
|
});
|
|
627
|
+
|
|
614
628
|
executeAfterWait(() => {
|
|
615
|
-
liveboardEmbed.navigateToLiveboard('lb1', 'viz1');
|
|
616
629
|
expect(onSpy).toHaveBeenCalledWith(HostEvent.Navigate, 'embed/viz/lb1/viz1');
|
|
617
630
|
done();
|
|
618
|
-
});
|
|
631
|
+
}, 1002);
|
|
619
632
|
});
|
|
620
633
|
|
|
621
634
|
test('navigateToLiveboard with preRender', async (done) => {
|
|
622
635
|
mockMessageChannel();
|
|
636
|
+
|
|
637
|
+
// mock getSessionInfo
|
|
638
|
+
jest.spyOn(SessionInfoService, 'getSessionInfo').mockResolvedValue({
|
|
639
|
+
releaseVersion: '1.0.0',
|
|
640
|
+
userGUID: '1234567890',
|
|
641
|
+
currentOrgId: 1,
|
|
642
|
+
privileges: [],
|
|
643
|
+
mixpanelToken: '1234567890',
|
|
644
|
+
});
|
|
645
|
+
|
|
623
646
|
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
624
647
|
...defaultViewConfig,
|
|
625
648
|
preRenderId: 'test',
|
|
@@ -631,12 +654,15 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
631
654
|
postMessageToParent(iframe.contentWindow, {
|
|
632
655
|
type: EmbedEvent.APP_INIT,
|
|
633
656
|
});
|
|
657
|
+
postMessageToParent(iframe.contentWindow, {
|
|
658
|
+
type: EmbedEvent.AuthInit,
|
|
659
|
+
});
|
|
634
660
|
});
|
|
635
661
|
executeAfterWait(() => {
|
|
636
662
|
liveboardEmbed.navigateToLiveboard('lb1', 'viz1');
|
|
637
663
|
expect(onSpy).toHaveBeenCalledWith(HostEvent.Navigate, 'embed/viz/lb1/viz1');
|
|
638
664
|
done();
|
|
639
|
-
});
|
|
665
|
+
}, 1002);
|
|
640
666
|
});
|
|
641
667
|
test('should set runtime parametere values in url params', async () => {
|
|
642
668
|
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
@@ -695,6 +721,12 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
695
721
|
});
|
|
696
722
|
|
|
697
723
|
describe('PreRender flow for liveboard embed', () => {
|
|
724
|
+
beforeAll(() => {
|
|
725
|
+
init({
|
|
726
|
+
thoughtSpotHost: "http://tshost",
|
|
727
|
+
authType: AuthType.None,
|
|
728
|
+
});
|
|
729
|
+
});
|
|
698
730
|
test('it should preRender generic with liveboard id is not passed', async (done) => {
|
|
699
731
|
const consoleSpy = jest.spyOn(console, 'error');
|
|
700
732
|
const libEmbed = new LiveboardEmbed(getRootEl(), {
|
|
@@ -761,7 +793,7 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
761
793
|
});
|
|
762
794
|
});
|
|
763
795
|
|
|
764
|
-
test('it should navigateToLiveboard with liveboard id is not passed', async (done) => {
|
|
796
|
+
test('it should navigateToLiveboard with liveboard id is not passed with EmbedListenerReady event', async (done) => {
|
|
765
797
|
mockMessageChannel();
|
|
766
798
|
const consoleSpy = jest.spyOn(console, 'error');
|
|
767
799
|
const testPreRenderId = 'testPreRender';
|
|
@@ -790,10 +822,19 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
790
822
|
libEmbed,
|
|
791
823
|
);
|
|
792
824
|
|
|
825
|
+
await executeAfterWait(() => {
|
|
826
|
+
const iframe = getIFrameEl();
|
|
827
|
+
postMessageToParent(iframe.contentWindow, {
|
|
828
|
+
type: EmbedEvent.EmbedListenerReady,
|
|
829
|
+
});
|
|
830
|
+
});
|
|
831
|
+
|
|
793
832
|
const testLiveboardId = 'testLiveboardId';
|
|
794
833
|
const newLibEmbed = new LiveboardEmbed(getRootEl(), {
|
|
795
834
|
preRenderId: testPreRenderId,
|
|
796
835
|
liveboardId: testLiveboardId,
|
|
836
|
+
vizId: 'testVizId',
|
|
837
|
+
activeTabId: 'testActiveTabId',
|
|
797
838
|
});
|
|
798
839
|
const navigateToLiveboardSpy = jest.spyOn(newLibEmbed, 'navigateToLiveboard');
|
|
799
840
|
await newLibEmbed.showPreRender();
|
|
@@ -804,7 +845,7 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
804
845
|
) as HTMLIFrameElement;
|
|
805
846
|
|
|
806
847
|
// should render the generic link
|
|
807
|
-
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(testLiveboardId);
|
|
848
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(testLiveboardId, 'testVizId', 'testActiveTabId');
|
|
808
849
|
expect(iFrame.src).toMatch(/http:\/\/tshost\/.*&isLiveboardEmbed=true.*#$/);
|
|
809
850
|
|
|
810
851
|
expect(consoleSpy).toHaveBeenCalledTimes(0);
|
|
@@ -812,6 +853,71 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
812
853
|
done();
|
|
813
854
|
});
|
|
814
855
|
});
|
|
856
|
+
|
|
857
|
+
test('it should navigateToLiveboard with liveboard id is not passed with AuthInit event', async (done) => {
|
|
858
|
+
mockMessageChannel();
|
|
859
|
+
const consoleSpy = jest.spyOn(console, 'error');
|
|
860
|
+
const testPreRenderId = 'testPreRender';
|
|
861
|
+
const libEmbed = new LiveboardEmbed(getRootEl(), {
|
|
862
|
+
preRenderId: testPreRenderId,
|
|
863
|
+
});
|
|
864
|
+
|
|
865
|
+
jest.spyOn(SessionInfoService, 'getSessionInfo').mockResolvedValue({
|
|
866
|
+
releaseVersion: '1.0.0',
|
|
867
|
+
userGUID: '1234567890',
|
|
868
|
+
currentOrgId: 1,
|
|
869
|
+
privileges: [],
|
|
870
|
+
mixpanelToken: '1234567890',
|
|
871
|
+
});
|
|
872
|
+
let resizeObserverCb: any;
|
|
873
|
+
(window as any).ResizeObserver =
|
|
874
|
+
window.ResizeObserver ||
|
|
875
|
+
jest.fn().mockImplementation((resizeObserverCbParam: any) => {
|
|
876
|
+
resizeObserverCb = resizeObserverCbParam;
|
|
877
|
+
return {
|
|
878
|
+
disconnect: jest.fn(),
|
|
879
|
+
observe: jest.fn(),
|
|
880
|
+
unobserve: jest.fn(),
|
|
881
|
+
};
|
|
882
|
+
});
|
|
883
|
+
await libEmbed.preRender();
|
|
884
|
+
await waitFor(() => !!getIFrameEl());
|
|
885
|
+
const ts = '__tsEmbed';
|
|
886
|
+
expect((document.getElementById(libEmbed.getPreRenderIds().wrapper) as any)[ts]).toEqual(
|
|
887
|
+
libEmbed,
|
|
888
|
+
);
|
|
889
|
+
const testLiveboardId = 'testLiveboardId';
|
|
890
|
+
const newLibEmbed = new LiveboardEmbed(getRootEl(), {
|
|
891
|
+
preRenderId: testPreRenderId,
|
|
892
|
+
liveboardId: testLiveboardId,
|
|
893
|
+
vizId: 'testVizId',
|
|
894
|
+
activeTabId: 'testActiveTabId',
|
|
895
|
+
});
|
|
896
|
+
const navigateToLiveboardSpy = jest.spyOn(newLibEmbed, 'navigateToLiveboard');
|
|
897
|
+
|
|
898
|
+
await newLibEmbed.showPreRender();
|
|
899
|
+
|
|
900
|
+
await executeAfterWait(() => {
|
|
901
|
+
const iFrame = document.getElementById(
|
|
902
|
+
newLibEmbed.getPreRenderIds().child,
|
|
903
|
+
) as HTMLIFrameElement;
|
|
904
|
+
postMessageToParent(iFrame.contentWindow, {
|
|
905
|
+
type: EmbedEvent.AuthInit,
|
|
906
|
+
});
|
|
907
|
+
});
|
|
908
|
+
|
|
909
|
+
|
|
910
|
+
await executeAfterWait(() => {
|
|
911
|
+
const iFrame = document.getElementById(
|
|
912
|
+
libEmbed.getPreRenderIds().child,
|
|
913
|
+
) as HTMLIFrameElement;
|
|
914
|
+
// should render the generic link
|
|
915
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(testLiveboardId, 'testVizId', 'testActiveTabId');
|
|
916
|
+
expect(iFrame.src).toMatch(/http:\/\/tshost\/.*&isLiveboardEmbed=true.*#$/);
|
|
917
|
+
expect(consoleSpy).toHaveBeenCalledTimes(0);
|
|
918
|
+
done();
|
|
919
|
+
}, 1005);
|
|
920
|
+
});
|
|
815
921
|
});
|
|
816
922
|
|
|
817
923
|
describe('LazyLoadingForFullHeight functionality', () => {
|
|
@@ -1085,4 +1191,157 @@ describe('Liveboard/viz embed tests', () => {
|
|
|
1085
1191
|
});
|
|
1086
1192
|
});
|
|
1087
1193
|
});
|
|
1194
|
+
|
|
1195
|
+
describe('Liveboard Embed Container Loading and PreRender', () => {
|
|
1196
|
+
beforeEach(() => {
|
|
1197
|
+
document.body.innerHTML = getDocumentBody();
|
|
1198
|
+
});
|
|
1199
|
+
|
|
1200
|
+
test('should call navigateToLiveboard after embed container is loaded in beforePrerenderVisible', async () => {
|
|
1201
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
1202
|
+
liveboardId,
|
|
1203
|
+
vizId,
|
|
1204
|
+
activeTabId,
|
|
1205
|
+
...defaultViewConfig,
|
|
1206
|
+
});
|
|
1207
|
+
|
|
1208
|
+
const navigateToLiveboardSpy = jest.spyOn(liveboardEmbed, 'navigateToLiveboard').mockResolvedValue(undefined);
|
|
1209
|
+
|
|
1210
|
+
// Mock embed container as not loaded initially
|
|
1211
|
+
liveboardEmbed.isEmbedContainerLoaded = false;
|
|
1212
|
+
|
|
1213
|
+
// Call beforePrerenderVisible
|
|
1214
|
+
liveboardEmbed['beforePrerenderVisible']();
|
|
1215
|
+
|
|
1216
|
+
// navigateToLiveboard should not be called immediately
|
|
1217
|
+
expect(navigateToLiveboardSpy).not.toHaveBeenCalled();
|
|
1218
|
+
|
|
1219
|
+
// Simulate embed container becoming ready
|
|
1220
|
+
liveboardEmbed.isEmbedContainerLoaded = true;
|
|
1221
|
+
liveboardEmbed['executeEmbedContainerReadyCallbacks']();
|
|
1222
|
+
|
|
1223
|
+
// Now navigateToLiveboard should be called
|
|
1224
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(liveboardId, vizId, activeTabId);
|
|
1225
|
+
});
|
|
1226
|
+
|
|
1227
|
+
test('should update currentLiveboardState for prerender object when embed container loads', async () => {
|
|
1228
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
1229
|
+
liveboardId,
|
|
1230
|
+
vizId,
|
|
1231
|
+
activeTabId,
|
|
1232
|
+
...defaultViewConfig,
|
|
1233
|
+
});
|
|
1234
|
+
|
|
1235
|
+
const mockPreRenderObj = {
|
|
1236
|
+
currentLiveboardState: {},
|
|
1237
|
+
};
|
|
1238
|
+
|
|
1239
|
+
jest.spyOn(liveboardEmbed as any, 'getPreRenderObj').mockReturnValue(mockPreRenderObj as any);
|
|
1240
|
+
jest.spyOn(liveboardEmbed, 'navigateToLiveboard').mockResolvedValue(undefined);
|
|
1241
|
+
|
|
1242
|
+
// Mock embed container as not loaded initially
|
|
1243
|
+
liveboardEmbed.isEmbedContainerLoaded = false;
|
|
1244
|
+
|
|
1245
|
+
// Call beforePrerenderVisible
|
|
1246
|
+
liveboardEmbed['beforePrerenderVisible']();
|
|
1247
|
+
|
|
1248
|
+
// Simulate embed container becoming ready
|
|
1249
|
+
liveboardEmbed.isEmbedContainerLoaded = true;
|
|
1250
|
+
liveboardEmbed['executeEmbedContainerReadyCallbacks']();
|
|
1251
|
+
|
|
1252
|
+
// Check that currentLiveboardState was updated
|
|
1253
|
+
expect(mockPreRenderObj.currentLiveboardState).toEqual({
|
|
1254
|
+
liveboardId,
|
|
1255
|
+
vizId,
|
|
1256
|
+
activeTabId,
|
|
1257
|
+
});
|
|
1258
|
+
});
|
|
1259
|
+
|
|
1260
|
+
test('should handle beforePrerenderVisible when embed container is already loaded', async () => {
|
|
1261
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
1262
|
+
liveboardId,
|
|
1263
|
+
vizId,
|
|
1264
|
+
activeTabId,
|
|
1265
|
+
...defaultViewConfig,
|
|
1266
|
+
});
|
|
1267
|
+
|
|
1268
|
+
const navigateToLiveboardSpy = jest.spyOn(liveboardEmbed, 'navigateToLiveboard').mockResolvedValue(undefined);
|
|
1269
|
+
|
|
1270
|
+
// Mock embed container as already loaded
|
|
1271
|
+
liveboardEmbed.isEmbedContainerLoaded = true;
|
|
1272
|
+
|
|
1273
|
+
// Call beforePrerenderVisible
|
|
1274
|
+
liveboardEmbed['beforePrerenderVisible']();
|
|
1275
|
+
|
|
1276
|
+
// navigateToLiveboard should be called immediately
|
|
1277
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(liveboardId, vizId, activeTabId);
|
|
1278
|
+
});
|
|
1279
|
+
|
|
1280
|
+
test('should handle beforePrerenderVisible without prerender object', async () => {
|
|
1281
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
1282
|
+
liveboardId,
|
|
1283
|
+
vizId,
|
|
1284
|
+
activeTabId,
|
|
1285
|
+
...defaultViewConfig,
|
|
1286
|
+
});
|
|
1287
|
+
|
|
1288
|
+
jest.spyOn(liveboardEmbed as any, 'getPreRenderObj').mockReturnValue(null);
|
|
1289
|
+
const navigateToLiveboardSpy = jest.spyOn(liveboardEmbed, 'navigateToLiveboard').mockResolvedValue(undefined);
|
|
1290
|
+
|
|
1291
|
+
// Mock embed container as not loaded initially
|
|
1292
|
+
liveboardEmbed.isEmbedContainerLoaded = false;
|
|
1293
|
+
|
|
1294
|
+
// Call beforePrerenderVisible
|
|
1295
|
+
liveboardEmbed['beforePrerenderVisible']();
|
|
1296
|
+
|
|
1297
|
+
// Simulate embed container becoming ready
|
|
1298
|
+
liveboardEmbed.isEmbedContainerLoaded = true;
|
|
1299
|
+
liveboardEmbed['executeEmbedContainerReadyCallbacks']();
|
|
1300
|
+
|
|
1301
|
+
// navigateToLiveboard should still be called
|
|
1302
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(liveboardId, vizId, activeTabId);
|
|
1303
|
+
});
|
|
1304
|
+
|
|
1305
|
+
test('should work with all liveboard parameters', async () => {
|
|
1306
|
+
const customLiveboardId = 'custom-liveboard-id';
|
|
1307
|
+
const customVizId = 'custom-viz-id';
|
|
1308
|
+
const customActiveTabId = 'custom-active-tab-id';
|
|
1309
|
+
|
|
1310
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
1311
|
+
liveboardId: customLiveboardId,
|
|
1312
|
+
vizId: customVizId,
|
|
1313
|
+
activeTabId: customActiveTabId,
|
|
1314
|
+
...defaultViewConfig,
|
|
1315
|
+
});
|
|
1316
|
+
|
|
1317
|
+
const navigateToLiveboardSpy = jest.spyOn(liveboardEmbed, 'navigateToLiveboard').mockResolvedValue(undefined);
|
|
1318
|
+
|
|
1319
|
+
// Mock embed container as already loaded
|
|
1320
|
+
liveboardEmbed.isEmbedContainerLoaded = true;
|
|
1321
|
+
|
|
1322
|
+
// Call beforePrerenderVisible
|
|
1323
|
+
liveboardEmbed['beforePrerenderVisible']();
|
|
1324
|
+
|
|
1325
|
+
// Check that all parameters are passed correctly
|
|
1326
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(customLiveboardId, customVizId, customActiveTabId);
|
|
1327
|
+
});
|
|
1328
|
+
|
|
1329
|
+
test('should work with minimal liveboard parameters', async () => {
|
|
1330
|
+
const liveboardEmbed = new LiveboardEmbed(getRootEl(), {
|
|
1331
|
+
liveboardId,
|
|
1332
|
+
...defaultViewConfig,
|
|
1333
|
+
});
|
|
1334
|
+
|
|
1335
|
+
const navigateToLiveboardSpy = jest.spyOn(liveboardEmbed, 'navigateToLiveboard').mockResolvedValue(undefined);
|
|
1336
|
+
|
|
1337
|
+
// Mock embed container as already loaded
|
|
1338
|
+
liveboardEmbed.isEmbedContainerLoaded = true;
|
|
1339
|
+
|
|
1340
|
+
// Call beforePrerenderVisible
|
|
1341
|
+
liveboardEmbed['beforePrerenderVisible']();
|
|
1342
|
+
|
|
1343
|
+
// Check that undefined parameters are passed correctly
|
|
1344
|
+
expect(navigateToLiveboardSpy).toHaveBeenCalledWith(liveboardId, undefined, undefined);
|
|
1345
|
+
});
|
|
1346
|
+
});
|
|
1088
1347
|
});
|
package/src/embed/liveboard.ts
CHANGED
|
@@ -408,6 +408,12 @@ export class LiveboardEmbed extends V1Embed {
|
|
|
408
408
|
* embedded Liveboard or visualization.
|
|
409
409
|
*/
|
|
410
410
|
protected getEmbedParams() {
|
|
411
|
+
const params = this.getEmbedParamsObject();
|
|
412
|
+
const queryParams = getQueryParamString(params, true);
|
|
413
|
+
return queryParams;
|
|
414
|
+
}
|
|
415
|
+
|
|
416
|
+
protected getEmbedParamsObject() {
|
|
411
417
|
let params: any = {};
|
|
412
418
|
params = this.getBaseQueryParams(params);
|
|
413
419
|
const {
|
|
@@ -511,9 +517,33 @@ export class LiveboardEmbed extends V1Embed {
|
|
|
511
517
|
params[Param.DataPanelV2Enabled] = dataPanelV2;
|
|
512
518
|
params[Param.EnableCustomColumnGroups] = enableCustomColumnGroups;
|
|
513
519
|
params[Param.CoverAndFilterOptionInPDF] = coverAndFilterOptionInPDF;
|
|
514
|
-
const queryParams = getQueryParamString(params, true);
|
|
515
520
|
|
|
516
|
-
|
|
521
|
+
if (oAuthPollingInterval !== undefined) {
|
|
522
|
+
params[Param.OauthPollingInterval] = oAuthPollingInterval;
|
|
523
|
+
}
|
|
524
|
+
|
|
525
|
+
if (isForceRedirect) {
|
|
526
|
+
params[Param.IsForceRedirect] = isForceRedirect;
|
|
527
|
+
}
|
|
528
|
+
|
|
529
|
+
if (dataSourceId !== undefined) {
|
|
530
|
+
params[Param.DataSourceId] = dataSourceId;
|
|
531
|
+
}
|
|
532
|
+
|
|
533
|
+
|
|
534
|
+
if (isLiveboardStylingAndGroupingEnabled !== undefined) {
|
|
535
|
+
params[Param.IsLiveboardStylingAndGroupingEnabled] = isLiveboardStylingAndGroupingEnabled;
|
|
536
|
+
}
|
|
537
|
+
|
|
538
|
+
params[Param.LiveboardHeaderSticky] = isLiveboardHeaderSticky;
|
|
539
|
+
params[Param.LiveboardHeaderV2] = isLiveboardCompactHeaderEnabled;
|
|
540
|
+
params[Param.ShowLiveboardVerifiedBadge] = showLiveboardVerifiedBadge;
|
|
541
|
+
params[Param.ShowLiveboardReverifyBanner] = showLiveboardReverifyBanner;
|
|
542
|
+
params[Param.HideIrrelevantFiltersInTab] = hideIrrelevantChipsInLiveboardTabs;
|
|
543
|
+
params[Param.DataPanelV2Enabled] = dataPanelV2;
|
|
544
|
+
params[Param.EnableCustomColumnGroups] = enableCustomColumnGroups;
|
|
545
|
+
params[Param.CoverAndFilterOptionInPDF] = coverAndFilterOptionInPDF;
|
|
546
|
+
return params;
|
|
517
547
|
}
|
|
518
548
|
|
|
519
549
|
private getIframeSuffixSrc(liveboardId: string, vizId: string, activeTabId: string) {
|
|
@@ -644,22 +674,30 @@ export class LiveboardEmbed extends V1Embed {
|
|
|
644
674
|
}
|
|
645
675
|
}
|
|
646
676
|
|
|
677
|
+
/**
|
|
678
|
+
* @hidden
|
|
679
|
+
* Internal state to track the current liveboard id.
|
|
680
|
+
* This is used to navigate to the correct liveboard when the prerender is visible.
|
|
681
|
+
*/
|
|
682
|
+
public currentLiveboardState = {
|
|
683
|
+
liveboardId: this.viewConfig.liveboardId,
|
|
684
|
+
vizId: this.viewConfig.vizId,
|
|
685
|
+
activeTabId: this.viewConfig.activeTabId,
|
|
686
|
+
};
|
|
687
|
+
|
|
647
688
|
protected beforePrerenderVisible(): void {
|
|
648
689
|
const embedObj = this.getPreRenderObj<LiveboardEmbed>();
|
|
649
690
|
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
embedObj.currentLiveboardId = libId;
|
|
661
|
-
});
|
|
662
|
-
}
|
|
691
|
+
this.executeAfterEmbedContainerLoaded(() => {
|
|
692
|
+
this.navigateToLiveboard(this.viewConfig.liveboardId, this.viewConfig.vizId, this.viewConfig.activeTabId);
|
|
693
|
+
if (embedObj) {
|
|
694
|
+
embedObj.currentLiveboardState = {
|
|
695
|
+
liveboardId: this.viewConfig.liveboardId,
|
|
696
|
+
vizId: this.viewConfig.vizId,
|
|
697
|
+
activeTabId: this.viewConfig.activeTabId,
|
|
698
|
+
};
|
|
699
|
+
}
|
|
700
|
+
});
|
|
663
701
|
}
|
|
664
702
|
|
|
665
703
|
protected async handleRenderForPrerender(): Promise<TsEmbed> {
|
|
@@ -733,16 +771,13 @@ export class LiveboardEmbed extends V1Embed {
|
|
|
733
771
|
return this;
|
|
734
772
|
}
|
|
735
773
|
|
|
736
|
-
public
|
|
737
|
-
|
|
738
|
-
public navigateToLiveboard(liveboardId: string, vizId?: string, activeTabId?: string, onNavigateCalled?: () => void) {
|
|
774
|
+
public navigateToLiveboard(liveboardId: string, vizId?: string, activeTabId?: string) {
|
|
739
775
|
const path = this.getIframeSuffixSrc(liveboardId, vizId, activeTabId);
|
|
740
776
|
this.viewConfig.liveboardId = liveboardId;
|
|
741
777
|
this.viewConfig.activeTabId = activeTabId;
|
|
742
778
|
this.viewConfig.vizId = vizId;
|
|
743
779
|
if (this.isRendered) {
|
|
744
|
-
|
|
745
|
-
this.triggerAfterLoad(HostEvent.Navigate, path.substring(1), onNavigateCalled);
|
|
780
|
+
this.trigger(HostEvent.Navigate, path.substring(1));
|
|
746
781
|
} else if (this.viewConfig.preRenderId) {
|
|
747
782
|
this.preRender(true);
|
|
748
783
|
} else {
|