@finos/legend-application-query 12.0.9 → 13.0.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.
Files changed (65) hide show
  1. package/lib/__lib__/LegendQueryEvent.d.ts +1 -0
  2. package/lib/__lib__/LegendQueryEvent.d.ts.map +1 -1
  3. package/lib/__lib__/LegendQueryEvent.js +1 -0
  4. package/lib/__lib__/LegendQueryEvent.js.map +1 -1
  5. package/lib/__lib__/LegendQueryTelemetryHelper.d.ts +7 -6
  6. package/lib/__lib__/LegendQueryTelemetryHelper.d.ts.map +1 -1
  7. package/lib/__lib__/LegendQueryTelemetryHelper.js +15 -12
  8. package/lib/__lib__/LegendQueryTelemetryHelper.js.map +1 -1
  9. package/lib/__lib__/LegendQueryUserDataHelper.d.ts +27 -0
  10. package/lib/__lib__/LegendQueryUserDataHelper.d.ts.map +1 -0
  11. package/lib/__lib__/LegendQueryUserDataHelper.js +63 -0
  12. package/lib/__lib__/LegendQueryUserDataHelper.js.map +1 -0
  13. package/lib/components/EditExistingQuerySetup.d.ts.map +1 -1
  14. package/lib/components/EditExistingQuerySetup.js +7 -71
  15. package/lib/components/EditExistingQuerySetup.js.map +1 -1
  16. package/lib/components/QueryEditor.d.ts.map +1 -1
  17. package/lib/components/QueryEditor.js +47 -97
  18. package/lib/components/QueryEditor.js.map +1 -1
  19. package/lib/components/QueryProductionizerSetup.d.ts.map +1 -1
  20. package/lib/components/QueryProductionizerSetup.js +6 -47
  21. package/lib/components/QueryProductionizerSetup.js.map +1 -1
  22. package/lib/components/QuerySetup.d.ts +3 -3
  23. package/lib/components/QuerySetup.d.ts.map +1 -1
  24. package/lib/components/QuerySetup.js +1 -1
  25. package/lib/components/QuerySetup.js.map +1 -1
  26. package/lib/index.css +2 -2
  27. package/lib/index.css.map +1 -1
  28. package/lib/index.d.ts +1 -1
  29. package/lib/index.d.ts.map +1 -1
  30. package/lib/index.js +1 -1
  31. package/lib/index.js.map +1 -1
  32. package/lib/package.json +1 -1
  33. package/lib/stores/EditExistingQuerySetupStore.d.ts +3 -12
  34. package/lib/stores/EditExistingQuerySetupStore.d.ts.map +1 -1
  35. package/lib/stores/EditExistingQuerySetupStore.js +27 -64
  36. package/lib/stores/EditExistingQuerySetupStore.js.map +1 -1
  37. package/lib/stores/LegendQueryApplicationPlugin.d.ts +4 -3
  38. package/lib/stores/LegendQueryApplicationPlugin.d.ts.map +1 -1
  39. package/lib/stores/LegendQueryApplicationPlugin.js.map +1 -1
  40. package/lib/stores/QueryEditorStore.d.ts +25 -39
  41. package/lib/stores/QueryEditorStore.d.ts.map +1 -1
  42. package/lib/stores/QueryEditorStore.js +44 -81
  43. package/lib/stores/QueryEditorStore.js.map +1 -1
  44. package/lib/stores/QueryProductionizerSetupStore.d.ts +4 -10
  45. package/lib/stores/QueryProductionizerSetupStore.d.ts.map +1 -1
  46. package/lib/stores/QueryProductionizerSetupStore.js +29 -62
  47. package/lib/stores/QueryProductionizerSetupStore.js.map +1 -1
  48. package/lib/stores/QuerySetupStore.d.ts.map +1 -1
  49. package/lib/stores/QuerySetupStore.js +4 -1
  50. package/lib/stores/QuerySetupStore.js.map +1 -1
  51. package/package.json +10 -10
  52. package/src/__lib__/LegendQueryEvent.ts +1 -0
  53. package/src/__lib__/LegendQueryTelemetryHelper.ts +19 -26
  54. package/src/__lib__/LegendQueryUserDataHelper.ts +92 -0
  55. package/src/components/EditExistingQuerySetup.tsx +10 -204
  56. package/src/components/QueryEditor.tsx +87 -291
  57. package/src/components/QueryProductionizerSetup.tsx +9 -124
  58. package/src/components/QuerySetup.tsx +1 -1
  59. package/src/index.ts +4 -1
  60. package/src/stores/EditExistingQuerySetupStore.ts +54 -87
  61. package/src/stores/LegendQueryApplicationPlugin.ts +4 -3
  62. package/src/stores/QueryEditorStore.ts +91 -107
  63. package/src/stores/QueryProductionizerSetupStore.ts +55 -84
  64. package/src/stores/QuerySetupStore.ts +10 -1
  65. package/tsconfig.json +1 -0
@@ -15,15 +15,9 @@
15
15
  */
16
16
 
17
17
  import {
18
- type SelectComponent,
19
18
  Dialog,
20
19
  PanelLoadingIndicator,
21
20
  BlankPanelContent,
22
- clsx,
23
- SearchIcon,
24
- TimesIcon,
25
- CheckSquareIcon,
26
- SquareIcon,
27
21
  DropdownMenu,
28
22
  MenuContent,
29
23
  MenuContentItem,
@@ -37,7 +31,6 @@ import {
37
31
  ModalHeader,
38
32
  ModalBody,
39
33
  ModalFooter,
40
- ModalTitle,
41
34
  ModalFooterButton,
42
35
  ManageSearchIcon,
43
36
  LightBulbIcon,
@@ -47,21 +40,19 @@ import {
47
40
  ExclamationTriangleIcon,
48
41
  PanelListItem,
49
42
  Button,
43
+ clsx,
50
44
  } from '@finos/legend-art';
51
- import { debounce } from '@finos/legend-shared';
52
45
  import { observer } from 'mobx-react-lite';
53
- import React, { Fragment, useEffect, useMemo, useRef, useState } from 'react';
46
+ import { Fragment, useEffect, useMemo, useRef } from 'react';
54
47
  import {
55
48
  type MappingQueryCreatorPathParams,
56
49
  type ExistingQueryEditorPathParams,
57
50
  type ServiceQueryCreatorPathParams,
58
51
  LEGEND_QUERY_QUERY_PARAM_TOKEN,
59
52
  LEGEND_QUERY_ROUTE_PATTERN_TOKEN,
60
- generateExistingQueryEditorRoute,
61
53
  generateQuerySetupRoute,
62
54
  } from '../__lib__/LegendQueryNavigation.js';
63
55
  import {
64
- type QueryEditorStore,
65
56
  QuerySaveAsState,
66
57
  createViewProjectHandler,
67
58
  createViewSDLCProjectHandler,
@@ -79,16 +70,16 @@ import {
79
70
  ServiceQueryCreatorStoreProvider,
80
71
  useQueryEditorStore,
81
72
  } from './QueryEditorStoreProvider.js';
82
- import type { RawLambda } from '@finos/legend-graph';
83
73
  import { flowResult } from 'mobx';
84
74
  import { useLegendQueryApplicationStore } from './LegendQueryFrameworkProvider.js';
85
75
  import {
86
76
  QueryBuilder,
87
77
  QueryBuilderNavigationBlocker,
78
+ QueryLoaderDialog,
88
79
  type QueryBuilderState,
89
80
  } from '@finos/legend-query-builder';
90
- import type { QueryEditorHelpMenuEntry } from '../stores/LegendQueryApplicationPlugin.js';
91
81
  import { QUERY_DOCUMENTATION_KEY } from '../application/LegendQueryDocumentation.js';
82
+ import { debounce } from '@finos/legend-shared';
92
83
  import { LegendQueryTelemetryHelper } from '../__lib__/LegendQueryTelemetryHelper.js';
93
84
 
94
85
  const QuerySaveAsDialogContent = observer(
@@ -194,238 +185,13 @@ const QuerySaveDialog = observer(() => {
194
185
  }}
195
186
  >
196
187
  <Modal darkMode={true} className="query-export">
197
- <ModalHeader title={'Create New Query'} />
188
+ <ModalHeader title="Create New Query" />
198
189
  {saveAsState && <QuerySaveAsDialogContent saveAsState={saveAsState} />}
199
190
  </Modal>
200
191
  </Dialog>
201
192
  );
202
193
  });
203
194
 
204
- const QueryLoader = observer(
205
- (props: {
206
- editorStore: QueryEditorStore;
207
- queryBuilderState: QueryBuilderState;
208
- }) => {
209
- const { editorStore, queryBuilderState } = props;
210
- const applicationStore = useApplicationStore();
211
-
212
- const queryFinderRef = useRef<SelectComponent>(null);
213
- const searchInputRef = useRef<HTMLInputElement>(null);
214
- const [selectedQueryID, setSelectedQueryID] = useState('');
215
- const [isMineOnly, setIsMineOnly] = useState(false);
216
- const [searchText, setSearchText] = useState('');
217
-
218
- // search text
219
- const debouncedLoadQueries = useMemo(
220
- () =>
221
- debounce((input: string): void => {
222
- flowResult(editorStore.queryLoaderState.loadQueries(input)).catch(
223
- applicationStore.alertUnhandledError,
224
- );
225
- }, 500),
226
- [applicationStore, editorStore.queryLoaderState],
227
- );
228
- const onSearchTextChange: React.ChangeEventHandler<HTMLInputElement> = (
229
- event,
230
- ) => {
231
- if (event.target.value !== searchText) {
232
- setSearchText(event.target.value);
233
- debouncedLoadQueries.cancel();
234
- debouncedLoadQueries(event.target.value);
235
- }
236
- };
237
- const clearQuerySearching = (): void => {
238
- setSearchText('');
239
- debouncedLoadQueries.cancel();
240
- debouncedLoadQueries('');
241
- };
242
- const toggleShowCurrentUserQueriesOnly = (): void => {
243
- editorStore.queryLoaderState.setShowCurrentUserQueriesOnly(
244
- !editorStore.queryLoaderState.showCurrentUserQueriesOnly,
245
- );
246
- setIsMineOnly(!isMineOnly);
247
- debouncedLoadQueries.cancel();
248
- debouncedLoadQueries(searchText);
249
- };
250
-
251
- useEffect(() => {
252
- flowResult(editorStore.queryLoaderState.loadQueries('')).catch(
253
- applicationStore.alertUnhandledError,
254
- );
255
- }, [applicationStore, editorStore.queryLoaderState]);
256
-
257
- // actions
258
- const loadQuery = (): void => {
259
- if (selectedQueryID) {
260
- queryBuilderState.changeDetectionState.alertUnsavedChanges(() => {
261
- editorStore.queryLoaderState.setIsQueryLoaderOpen(false);
262
- applicationStore.navigationService.navigator.goToLocation(
263
- generateExistingQueryEditorRoute(selectedQueryID),
264
- { ignoreBlocking: true },
265
- );
266
- });
267
- }
268
- };
269
-
270
- // life-cycle
271
- const close = (): void => {
272
- editorStore.queryLoaderState.setIsQueryLoaderOpen(false);
273
- editorStore.queryLoaderState.reset();
274
- };
275
- const onEnter = (): void => queryFinderRef.current?.focus();
276
-
277
- return (
278
- <Dialog
279
- open={editorStore.queryLoaderState.isQueryLoaderOpen}
280
- onClose={close}
281
- TransitionProps={{
282
- onEnter,
283
- }}
284
- classes={{ container: 'search-modal__container' }}
285
- PaperProps={{ classes: { root: 'search-modal__inner-container' } }}
286
- >
287
- <Modal darkMode={true} className="search-modal">
288
- <ModalTitle title="Load Query" />
289
- <div className="query-editor__query-loader__filter-section">
290
- <div className="query-editor__query-loader__filter-section__section__toggler">
291
- <button
292
- className={clsx(
293
- 'query-editor__query-loader__filter-section__section__toggler__btn',
294
- {
295
- 'query-editor__query-loader__filter-section__section__toggler__btn--toggled':
296
- isMineOnly,
297
- },
298
- )}
299
- onClick={toggleShowCurrentUserQueriesOnly}
300
- tabIndex={-1}
301
- >
302
- {isMineOnly ? <CheckSquareIcon /> : <SquareIcon />}
303
- </button>
304
- <div
305
- className="query-editor__query-loader__filter-section__section__toggler__prompt"
306
- onClick={toggleShowCurrentUserQueriesOnly}
307
- >
308
- Mine Only
309
- </div>
310
- </div>
311
- </div>
312
- <div className="query-editor__query-loader__search-section">
313
- <div className="query-editor__query-loader__search-section__input__container">
314
- <input
315
- ref={searchInputRef}
316
- className={clsx(
317
- 'query-editor__query-loader__search-section__input input--dark',
318
- {
319
- 'query-editor__query-loader__search-section__input--searching':
320
- searchText,
321
- },
322
- )}
323
- onChange={onSearchTextChange}
324
- value={searchText}
325
- placeholder="Search a query by name"
326
- />
327
- {!searchText ? (
328
- <div className="query-editor__query-loader__search-section__input__search__icon">
329
- <SearchIcon />
330
- </div>
331
- ) : (
332
- <>
333
- <button
334
- className="query-editor__query-loader__search-section__input__clear-btn"
335
- tabIndex={-1}
336
- onClick={clearQuerySearching}
337
- title="Clear"
338
- >
339
- <TimesIcon />
340
- </button>
341
- </>
342
- )}
343
- </div>
344
- </div>
345
- <div className="query-editor__query-loader__body">
346
- {editorStore.queryLoaderState.loadQueriesState.hasCompleted && (
347
- <>
348
- {editorStore.queryLoaderState.queries.length > 0 && (
349
- <>
350
- <table className="table">
351
- <thead>
352
- <tr>
353
- <th className="table__cell--left">Name</th>
354
- <th className="table__cell--left">Author</th>
355
- <th className="table__cell--left">Version</th>
356
- </tr>
357
- </thead>
358
- <tbody>
359
- {editorStore.queryLoaderState.queries.map((query) => (
360
- <tr
361
- key={query.id}
362
- className={clsx(
363
- 'query-editor__query-loader__body__table__row',
364
- {
365
- 'query-editor__query-loader__body__table__row--selected':
366
- selectedQueryID === query.id,
367
- },
368
- )}
369
- onClick={(event) => setSelectedQueryID(query.id)}
370
- >
371
- <td className="table__cell--left">{query.name}</td>
372
- <td className="table__cell--left">
373
- {query.owner ?? 'anonymous'}
374
- </td>
375
- <td className="table__cell--left">
376
- {query.versionId}
377
- </td>
378
- </tr>
379
- ))}
380
- </tbody>
381
- </table>
382
- </>
383
- )}
384
- {editorStore.queryLoaderState.queries.length === 0 && (
385
- <BlankPanelContent>No query available</BlankPanelContent>
386
- )}
387
- </>
388
- )}
389
- {!editorStore.queryLoaderState.loadQueriesState.hasCompleted && (
390
- <>
391
- <PanelLoadingIndicator
392
- isLoading={
393
- !editorStore.queryLoaderState.loadQueriesState.hasCompleted
394
- }
395
- />
396
- <BlankPanelContent>Loading queries...</BlankPanelContent>
397
- </>
398
- )}
399
- </div>
400
- <div className="search-modal__actions">
401
- <button
402
- className="btn btn--dark"
403
- onClick={loadQuery}
404
- disabled={selectedQueryID === ''}
405
- >
406
- Load Query
407
- </button>
408
- <button className="btn btn--dark" onClick={close}>
409
- Close
410
- </button>
411
- </div>
412
- </Modal>
413
- </Dialog>
414
- );
415
- },
416
- );
417
-
418
- const HelpMenuContentItemRenderer = (
419
- props: QueryEditorHelpMenuEntry,
420
- ): React.ReactElement => (
421
- <MenuContentItem title={props.title ?? ''} onClick={props.onClick}>
422
- {props.icon && <MenuContentItemIcon>{props.icon}</MenuContentItemIcon>}
423
- <MenuContentItemLabel className="query-builder__sub-header__menu-content">
424
- {props.label}
425
- </MenuContentItemLabel>
426
- </MenuContentItem>
427
- );
428
-
429
195
  const QueryEditorHeaderContent = observer(
430
196
  (props: { queryBuilderState: QueryBuilderState }) => {
431
197
  const { queryBuilderState } = props;
@@ -435,7 +201,7 @@ const QueryEditorHeaderContent = observer(
435
201
 
436
202
  // actions
437
203
  const openQueryLoader = (): void => {
438
- editorStore.queryLoaderState.setIsQueryLoaderOpen(true);
204
+ editorStore.queryLoaderState.setQueryLoaderDialogOpen(true);
439
205
  };
440
206
  const viewProject = (): void => {
441
207
  LegendQueryTelemetryHelper.logEvent_QueryViewProjectLaunched(
@@ -472,64 +238,69 @@ const QueryEditorHeaderContent = observer(
472
238
 
473
239
  const renameRef = useRef<HTMLInputElement>(null);
474
240
 
475
- const updateQuery = (): void => {
476
- queryBuilderState
477
- .saveQuery(async (lambda: RawLambda) => {
241
+ const updateQuery = applicationStore.guardUnhandledError(
242
+ async (): Promise<void> => {
243
+ try {
244
+ const lambda = queryBuilderState.buildQuery();
478
245
  editorStore.setRenameState(
479
246
  new QueryRenameState(
480
247
  editorStore,
481
248
  queryBuilderState,
482
249
  lambda,
483
- await editorStore.getExportConfiguration(lambda, {
250
+ await editorStore.getPersistConfiguration(lambda, {
484
251
  update: true,
485
252
  }),
486
253
  ),
487
254
  );
488
- })
489
- .then(() => {
490
255
  renameRef.current?.select();
491
- })
492
- .catch(applicationStore.alertUnhandledError);
493
- };
494
-
495
- const renameQuery = applicationStore.guardUnhandledError(async () => {
496
- await renameState?.renameQuery();
497
- });
256
+ } catch {
257
+ // do nothing
258
+ }
259
+ },
260
+ );
498
261
 
499
- const saveQuery = (): void => {
500
- queryBuilderState
501
- .saveQuery(async (lambda: RawLambda) => {
262
+ const saveQuery = applicationStore.guardUnhandledError(
263
+ async (): Promise<void> => {
264
+ try {
265
+ const lambda = queryBuilderState.buildQuery();
502
266
  editorStore.setSaveState(
503
267
  new QuerySaveState(
504
268
  editorStore,
505
269
  queryBuilderState,
506
270
  lambda,
507
- await editorStore.getExportConfiguration(lambda, {
271
+ await editorStore.getPersistConfiguration(lambda, {
508
272
  update: true,
509
273
  }),
510
274
  ),
511
275
  );
512
- flowResult(editorStore.saveState?.saveQuery()).catch(
276
+ await flowResult(editorStore.saveState?.saveQuery()).catch(
513
277
  applicationStore.alertUnhandledError,
514
278
  );
515
- })
516
- .catch(applicationStore.alertUnhandledError);
517
- };
279
+ } catch {
280
+ // do nothing
281
+ }
282
+ },
283
+ );
518
284
 
519
- const saveAsQuery = (): void => {
520
- queryBuilderState
521
- .saveQuery(async (lambda: RawLambda) => {
285
+ const saveAsQuery = applicationStore.guardUnhandledError(
286
+ async (): Promise<void> => {
287
+ try {
288
+ const lambda = queryBuilderState.buildQuery();
522
289
  editorStore.setSaveAsState(
523
290
  new QuerySaveAsState(
524
291
  editorStore,
525
292
  queryBuilderState,
526
293
  lambda,
527
- await editorStore.getExportConfiguration(lambda),
294
+ await editorStore.getPersistConfiguration(lambda, {
295
+ update: true,
296
+ }),
528
297
  ),
529
298
  );
530
- })
531
- .catch(applicationStore.alertUnhandledError);
532
- };
299
+ } catch {
300
+ // do nothing
301
+ }
302
+ },
303
+ );
533
304
 
534
305
  const toggleAssistant = (): void =>
535
306
  applicationStore.assistantService.toggleAssistant();
@@ -546,6 +317,14 @@ const QueryEditorHeaderContent = observer(
546
317
  }
547
318
  };
548
319
 
320
+ const renameQuery = (): void => {
321
+ if (renameState) {
322
+ flowResult(renameState.renameQuery()).catch(
323
+ applicationStore.alertUnhandledError,
324
+ );
325
+ }
326
+ };
327
+
549
328
  const changeQueryName: React.ChangeEventHandler<HTMLInputElement> = (
550
329
  event,
551
330
  ) => renameState?.setQueryName(event.target.value);
@@ -583,8 +362,20 @@ const QueryEditorHeaderContent = observer(
583
362
 
584
363
  const extraHelpMenuContentItems = applicationStore.pluginManager
585
364
  .getApplicationPlugins()
586
- .flatMap((plugin) => plugin.getExtraQueryEditorHelpMenuEntries?.() ?? [])
587
- .map((item) => <>{HelpMenuContentItemRenderer(item)}</>);
365
+ .flatMap(
366
+ (plugin) =>
367
+ plugin.getExtraQueryEditorHelpMenuActionConfigurations?.() ?? [],
368
+ )
369
+ .map((item) => (
370
+ <MenuContentItem
371
+ key={item.key}
372
+ title={item.title ?? ''}
373
+ onClick={item.onClick}
374
+ >
375
+ {item.icon && <MenuContentItemIcon>{item.icon}</MenuContentItemIcon>}
376
+ <MenuContentItemLabel>{item.label}</MenuContentItemLabel>
377
+ </MenuContentItem>
378
+ ));
588
379
 
589
380
  return (
590
381
  <div className="query-editor__header__content">
@@ -606,7 +397,7 @@ const QueryEditorHeaderContent = observer(
606
397
  {isExistingQueryName && (
607
398
  <div
608
399
  className="input--with-validation__caution"
609
- title={`Query named '${isExistingQueryName}' already exists`}
400
+ title={`Query with name '${isExistingQueryName}' already exists`}
610
401
  >
611
402
  <ExclamationTriangleIcon className="input--with-validation__caution__indicator" />
612
403
  </div>
@@ -662,7 +453,7 @@ const QueryEditorHeaderContent = observer(
662
453
  disabled={
663
454
  editorStore.isSaveActionDisabled ||
664
455
  !editorStore.title ||
665
- queryBuilderState.saveQueryProgressState.isInProgress
456
+ Boolean(editorStore.saveState?.saveQueryState.isInProgress)
666
457
  }
667
458
  onClick={saveQuery}
668
459
  title="Save query"
@@ -672,7 +463,10 @@ const QueryEditorHeaderContent = observer(
672
463
  </Button>
673
464
  <Button
674
465
  className="query-editor__header__action btn--dark"
675
- disabled={editorStore.isSaveActionDisabled}
466
+ disabled={
467
+ editorStore.isSaveActionDisabled ||
468
+ Boolean(editorStore.saveAsState?.createQueryState.isInProgress)
469
+ }
676
470
  onClick={saveAsQuery}
677
471
  title="Save as new query"
678
472
  >
@@ -691,7 +485,7 @@ const QueryEditorHeaderContent = observer(
691
485
  {queryDocEntry && (
692
486
  <MenuContentItem onClick={openQueryTutorial}>
693
487
  <MenuContentItemIcon>{null}</MenuContentItemIcon>
694
- <MenuContentItemLabel className="query-builder__sub-header__menu-content">
488
+ <MenuContentItemLabel>
695
489
  Open Documentation
696
490
  </MenuContentItemLabel>
697
491
  </MenuContentItem>
@@ -703,7 +497,7 @@ const QueryEditorHeaderContent = observer(
703
497
  <CheckIcon />
704
498
  ) : null}
705
499
  </MenuContentItemIcon>
706
- <MenuContentItemLabel className="query-builder__sub-header__menu-content">
500
+ <MenuContentItemLabel>
707
501
  Show Virtual Assistant
708
502
  </MenuContentItemLabel>
709
503
  </MenuContentItem>
@@ -711,23 +505,23 @@ const QueryEditorHeaderContent = observer(
711
505
  }
712
506
  >
713
507
  <div
714
- className=" query-editor__header__action__label"
508
+ className="query-editor__header__action__label"
715
509
  title="See more options"
716
510
  >
717
- Help
511
+ Help...
718
512
  </div>
719
- <CaretDownIcon />
513
+ <CaretDownIcon className="query-editor__header__action__dropdown-trigger" />
720
514
  </DropdownMenu>
721
- {editorStore.queryLoaderState.isQueryLoaderOpen && (
722
- <QueryLoader
723
- editorStore={editorStore}
724
- queryBuilderState={queryBuilderState}
515
+ {editorStore.queryLoaderState.isQueryLoaderDialogOpen && (
516
+ <QueryLoaderDialog
517
+ queryLoaderState={editorStore.queryLoaderState}
518
+ title="Load query"
725
519
  />
726
520
  )}
727
521
  <button
728
522
  title="Toggle light/dark mode"
729
523
  onClick={TEMPORARY__toggleLightDarkMode}
730
- className="query-editor__header__action"
524
+ className="query-editor__header__action query-editor__header__action__theme-toggler"
731
525
  >
732
526
  {applicationStore.layoutService
733
527
  .TEMPORARY__isLightColorThemeEnabled ? (
@@ -746,6 +540,15 @@ const QueryEditorHeaderContent = observer(
746
540
  disabled={editorStore.isViewProjectActionDisabled}
747
541
  content={
748
542
  <MenuContent>
543
+ {/* TODO: remove this and move it to inline editing directly on the title */}
544
+ <MenuContentItem
545
+ className="query-editor__header__action__options"
546
+ onClick={updateQuery}
547
+ disabled={!editorStore.title}
548
+ >
549
+ Rename Query
550
+ </MenuContentItem>
551
+
749
552
  <MenuContentItem
750
553
  className="query-editor__header__action__options"
751
554
  disabled={editorStore.isViewProjectActionDisabled}
@@ -760,13 +563,6 @@ const QueryEditorHeaderContent = observer(
760
563
  >
761
564
  Go to SDLC project
762
565
  </MenuContentItem>
763
- <MenuContentItem
764
- className="query-editor__header__action__options"
765
- onClick={updateQuery}
766
- disabled={!editorStore.title}
767
- >
768
- Rename Query
769
- </MenuContentItem>
770
566
  </MenuContent>
771
567
  }
772
568
  >
@@ -776,7 +572,7 @@ const QueryEditorHeaderContent = observer(
776
572
  >
777
573
  More Actions...
778
574
  </div>
779
- <CaretDownIcon />
575
+ <CaretDownIcon className="query-editor__header__action__dropdown-trigger" />
780
576
  </DropdownMenu>
781
577
 
782
578
  {editorStore.saveAsState && <QuerySaveDialog />}