Skip to content

Commit bb70acb

Browse files
committed
These changes are in response to PR comments
1 parent 3441efc commit bb70acb

File tree

1 file changed

+205
-110
lines changed

1 file changed

+205
-110
lines changed

public/components/integrations/components/setup_integration.tsx

+205-110
Original file line numberDiff line numberDiff line change
@@ -123,9 +123,7 @@ const runQuery = async (
123123
* @returns A string representing the fully qualified table name in the format: dataSource.database.table
124124
*/
125125
const makeTableName = (config: IntegrationSetupInputs): string => {
126-
return `${config.connectionDataSource}.${config.databaseName || 'default'}.${
127-
config.connectionTableName
128-
}`;
126+
return `${config.connectionDataSource}.${config.databaseName}.${config.connectionTableName}`;
129127
};
130128

131129
const prepareQuery = (query: string, config: IntegrationSetupInputs): string => {
@@ -149,22 +147,19 @@ const prepareQuery = (query: string, config: IntegrationSetupInputs): string =>
149147
};
150148

151149
/**
152-
* Adds a new integration by setting up necessary database configurations and running required queries.
150+
* Handles the integration setup process based on the connection type.
153151
*
154152
* @param {Object} params - The parameters object
155153
* @param {IntegrationSetupInputs} params.config - Configuration settings for the integration setup
156154
* @param {IntegrationConfig} params.integration - Integration configuration details
157-
* @param {Function} params.setLoading - Callback function to update loading state
155+
* @param {Function} params.setLoading - Callback function to set loading state
158156
* @param {Function} params.setCalloutLikeToast - Callback function to display toast notifications
159157
* @param {string} [params.dataSourceMDSId] - Optional MDS ID for the data source
160158
* @param {string} [params.dataSourceMDSLabel] - Optional MDS label for the data source
161-
* @param {Function} [params.setIsInstalling] - Optional callback to update installation status
159+
* @param {Function} [params.setIsInstalling] - Optional callback to set installation status
162160
*
163-
* @throws Will throw an error if database creation or query execution fails
164-
*
165-
* The function handles different connection types:
166-
* - For 'index' type: Sets up index-based integration
167-
* - For 's3' type: Creates database, runs asset queries, and sets up S3 integration
161+
* @throws {Error} Throws an error if the connection type is invalid
162+
* @returns {Promise<void>} A promise that resolves when the integration is added
168163
*/
169164
const addIntegration = async ({
170165
config,
@@ -182,112 +177,211 @@ const addIntegration = async ({
182177
dataSourceMDSId?: string;
183178
dataSourceMDSLabel?: string;
184179
setIsInstalling?: (isInstalling: boolean, success?: boolean) => void;
185-
}) => {
180+
}): Promise<void> => {
186181
setLoading(true);
182+
183+
if (config.connectionType === 'index') {
184+
await addNativeIntegration({
185+
config,
186+
integration,
187+
setLoading,
188+
setCalloutLikeToast,
189+
dataSourceMDSId,
190+
dataSourceMDSLabel,
191+
setIsInstalling,
192+
});
193+
} else if (config.connectionType === 's3') {
194+
await addFlintIntegration({
195+
config,
196+
integration,
197+
setLoading,
198+
setCalloutLikeToast,
199+
dataSourceMDSId,
200+
dataSourceMDSLabel,
201+
setIsInstalling,
202+
});
203+
} else {
204+
console.error('Invalid data source type');
205+
setLoading(false);
206+
}
207+
};
208+
209+
/**
210+
* Handles the installation of an integration index by processing the configuration and making the integration request.
211+
*
212+
* @param {Object} params - The parameters object
213+
* @param {IntegrationSetupInputs} params.config - Configuration inputs for the integration setup
214+
* @param {IntegrationConfig} params.integration - Integration configuration object
215+
* @param {Function} params.setLoading - Function to set the loading state
216+
* @param {Function} params.setCalloutLikeToast - Function to display toast notifications
217+
* @param {string} [params.dataSourceMDSId] - Optional MDS ID for the data source
218+
* @param {string} [params.dataSourceMDSLabel] - Optional MDS label for the data source
219+
* @param {Function} [params.setIsInstalling] - Optional function to set installation status
220+
*
221+
* @returns {Promise<void>} A promise that resolves when the installation is complete
222+
*
223+
* @example
224+
* await addNativeIntegration({
225+
* config: setupInputs,
226+
* integration: integrationConfig,
227+
* setLoading: (loading) => setLoadingState(loading),
228+
* setCalloutLikeToast: (title, color, text) => showToast(title, color, text)
229+
* });
230+
*/
231+
const addNativeIntegration = async ({
232+
config,
233+
integration,
234+
setLoading,
235+
setCalloutLikeToast,
236+
dataSourceMDSId,
237+
dataSourceMDSLabel,
238+
setIsInstalling,
239+
}: {
240+
config: IntegrationSetupInputs;
241+
integration: IntegrationConfig;
242+
setLoading: (loading: boolean) => void;
243+
setCalloutLikeToast: (title: string, color?: Color, text?: string) => void;
244+
dataSourceMDSId?: string;
245+
dataSourceMDSLabel?: string;
246+
setIsInstalling?: (isInstalling: boolean, success?: boolean) => void;
247+
}): Promise<void> => {
248+
let enabledWorkflows: string[] | undefined;
249+
if (integration.workflows) {
250+
enabledWorkflows = integration.workflows
251+
.filter((w) =>
252+
w.applicable_data_sources ? w.applicable_data_sources.includes('index') : true
253+
)
254+
.map((w) => w.name);
255+
}
256+
257+
const res = await addIntegrationRequest({
258+
addSample: false,
259+
templateName: integration.name,
260+
integration,
261+
setToast: setCalloutLikeToast,
262+
dataSourceMDSId,
263+
dataSourceMDSLabel,
264+
name: config.displayName,
265+
indexPattern: config.connectionDataSource,
266+
skipRedirect: setIsInstalling ? true : false,
267+
workflows: enabledWorkflows,
268+
});
269+
270+
if (setIsInstalling) {
271+
setIsInstalling(false, res);
272+
}
273+
if (!res) {
274+
setLoading(false);
275+
}
276+
};
277+
278+
/**
279+
* Handles the installation process for S3 integration by creating a database (if specified),
280+
* processing integration assets, and executing necessary queries.
281+
*
282+
* @param {Object} params - The parameters object
283+
* @param {IntegrationSetupInputs} params.config - Configuration settings for the integration setup
284+
* @param {IntegrationConfig} params.integration - Integration configuration details
285+
* @param {Function} params.setLoading - Callback function to set loading state
286+
* @param {Function} params.setCalloutLikeToast - Callback function to display toast notifications
287+
* @param {string} [params.dataSourceMDSId] - Optional MDS ID for the data source
288+
* @param {string} [params.dataSourceMDSLabel] - Optional MDS label for the data source
289+
* @param {Function} [params.setIsInstalling] - Optional callback to set installation status
290+
*
291+
* @returns {Promise<void>} A promise that resolves when the installation is complete
292+
*
293+
* @throws Will set error toast if database creation fails or integration addition fails
294+
*/
295+
const addFlintIntegration = async ({
296+
config,
297+
integration,
298+
setLoading,
299+
setCalloutLikeToast,
300+
dataSourceMDSId,
301+
dataSourceMDSLabel,
302+
setIsInstalling,
303+
}: {
304+
config: IntegrationSetupInputs;
305+
integration: IntegrationConfig;
306+
setLoading: (loading: boolean) => void;
307+
setCalloutLikeToast: (title: string, color?: Color, text?: string) => void;
308+
dataSourceMDSId?: string;
309+
dataSourceMDSLabel?: string;
310+
setIsInstalling?: (isInstalling: boolean, success?: boolean) => void;
311+
}): Promise<void> => {
187312
let sessionId: string | undefined;
188-
try {
189-
// First create the database if one is specified
190-
if (config.databaseName) {
191-
const createDbQuery = `CREATE DATABASE IF NOT EXISTS ${config.databaseName}`;
192-
const result = await runQuery(
193-
createDbQuery,
194-
config.connectionDataSource,
195-
sessionId,
196-
dataSourceMDSId
197-
);
198313

199-
if (!result.ok) {
200-
setLoading(false);
201-
setCalloutLikeToast('Failed to create database', 'danger', result.error.message);
202-
return;
203-
}
204-
sessionId = result.value.sessionId;
314+
// Create database if specified
315+
if (config.databaseName) {
316+
const createDbQuery = `CREATE DATABASE IF NOT EXISTS ${config.databaseName}`;
317+
const result = await runQuery(
318+
createDbQuery,
319+
config.connectionDataSource,
320+
sessionId,
321+
dataSourceMDSId
322+
);
323+
324+
if (!result.ok) {
325+
setLoading(false);
326+
setCalloutLikeToast('Failed to create database', 'danger', result.error.message);
327+
return;
205328
}
329+
sessionId = result.value.sessionId;
330+
}
206331

207-
if (config.connectionType === 'index') {
208-
let enabledWorkflows: string[] | undefined;
209-
if (integration.workflows) {
210-
enabledWorkflows = integration.workflows
211-
.filter((w) =>
212-
w.applicable_data_sources ? w.applicable_data_sources.includes('index') : true
213-
)
214-
.map((w) => w.name);
215-
}
216-
const res = await addIntegrationRequest({
217-
addSample: false,
218-
templateName: integration.name,
219-
integration,
220-
setToast: setCalloutLikeToast,
221-
dataSourceMDSId,
222-
dataSourceMDSLabel,
223-
name: config.displayName,
224-
indexPattern: config.connectionDataSource,
225-
skipRedirect: setIsInstalling ? true : false,
226-
workflows: enabledWorkflows,
227-
});
228-
if (setIsInstalling) {
229-
setIsInstalling(false, res);
230-
}
231-
if (!res) {
232-
setLoading(false);
233-
}
234-
} else if (config.connectionType === 's3') {
235-
const http = coreRefs.http!;
332+
// Process integration assets
333+
const http = coreRefs.http!;
334+
const assets: { data: ParsedIntegrationAsset[] } = await http.get(
335+
`${INTEGRATIONS_BASE}/repository/${integration.name}/assets`
336+
);
236337

237-
const assets: { data: ParsedIntegrationAsset[] } = await http.get(
238-
`${INTEGRATIONS_BASE}/repository/${integration.name}/assets`
239-
);
240-
for (const query of assets.data.filter(
241-
(a: ParsedIntegrationAsset): a is ParsedIntegrationAsset & { type: 'query' } =>
242-
a.type === 'query'
243-
)) {
244-
// Skip any queries that have conditional workflows but aren't enabled
245-
if (query.workflows && !query.workflows.some((w) => config.enabledWorkflows.includes(w))) {
246-
continue;
247-
}
248-
249-
const queryStr = prepareQuery(query.query, config);
250-
const result = await runQuery(
251-
queryStr,
252-
config.connectionDataSource,
253-
sessionId,
254-
dataSourceMDSId
255-
);
256-
if (!result.ok) {
257-
setLoading(false);
258-
setCalloutLikeToast('Failed to add integration', 'danger', result.error.message);
259-
return;
260-
}
261-
sessionId = result.value.sessionId ?? sessionId;
262-
}
263-
// Once everything is ready, add the integration to the new datasource as usual
264-
const res = await addIntegrationRequest({
265-
addSample: false,
266-
templateName: integration.name,
267-
integration,
268-
setToast: setCalloutLikeToast,
269-
dataSourceMDSId,
270-
dataSourceMDSLabel,
271-
name: config.displayName,
272-
indexPattern: `flint_${config.connectionDataSource}_${config.databaseName}_${config.connectionTableName}__*`,
273-
workflows: config.enabledWorkflows,
274-
skipRedirect: setIsInstalling ? true : false,
275-
dataSourceInfo: {
276-
dataSource: config.connectionDataSource,
277-
tableName: makeTableName(config),
278-
},
279-
});
280-
if (setIsInstalling) {
281-
setIsInstalling(false, res);
282-
}
283-
if (!res) {
284-
setLoading(false);
285-
}
286-
} else {
287-
console.error('Invalid data source type');
338+
// Execute queries
339+
for (const query of assets.data.filter(
340+
(a: ParsedIntegrationAsset): a is ParsedIntegrationAsset & { type: 'query' } =>
341+
a.type === 'query'
342+
)) {
343+
if (query.workflows && !query.workflows.some((w) => config.enabledWorkflows.includes(w))) {
344+
continue;
345+
}
346+
347+
const queryStr = prepareQuery(query.query, config);
348+
const result = await runQuery(
349+
queryStr,
350+
config.connectionDataSource,
351+
sessionId,
352+
dataSourceMDSId
353+
);
354+
355+
if (!result.ok) {
356+
setLoading(false);
357+
setCalloutLikeToast('Failed to add integration', 'danger', result.error.message);
358+
return;
288359
}
289-
} catch (error) {
290-
setCalloutLikeToast('Failed to add integration', 'danger');
360+
sessionId = result.value.sessionId ?? sessionId;
361+
}
362+
363+
// Add integration to the new datasource
364+
const res = await addIntegrationRequest({
365+
addSample: false,
366+
templateName: integration.name,
367+
integration,
368+
setToast: setCalloutLikeToast,
369+
dataSourceMDSId,
370+
dataSourceMDSLabel,
371+
name: config.displayName,
372+
indexPattern: `flint_${config.connectionDataSource}_${config.databaseName}_${config.connectionTableName}__*`,
373+
workflows: config.enabledWorkflows,
374+
skipRedirect: setIsInstalling ? true : false,
375+
dataSourceInfo: {
376+
dataSource: config.connectionDataSource,
377+
tableName: makeTableName(config),
378+
},
379+
});
380+
381+
if (setIsInstalling) {
382+
setIsInstalling(false, res);
383+
}
384+
if (!res) {
291385
setLoading(false);
292386
}
293387
};
@@ -452,6 +546,7 @@ export function SetupIntegrationForm({
452546
connectionLocation: '',
453547
checkpointLocation: '',
454548
connectionTableName: integration,
549+
databaseName: 'default',
455550
enabledWorkflows: [],
456551
});
457552

0 commit comments

Comments
 (0)