@finos/legend-query-builder 4.14.37 → 4.14.39
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/lib/__lib__/QueryBuilderTesting.d.ts +2 -1
- package/lib/__lib__/QueryBuilderTesting.d.ts.map +1 -1
- package/lib/__lib__/QueryBuilderTesting.js +1 -0
- package/lib/__lib__/QueryBuilderTesting.js.map +1 -1
- package/lib/components/QueryBuilder.d.ts.map +1 -1
- package/lib/components/QueryBuilder.js +10 -9
- package/lib/components/QueryBuilder.js.map +1 -1
- package/lib/components/QueryBuilderParametersPanel.js +2 -2
- package/lib/components/QueryBuilderParametersPanel.js.map +1 -1
- package/lib/components/QueryBuilderPropertyExpressionEditor.d.ts +0 -2
- package/lib/components/QueryBuilderPropertyExpressionEditor.d.ts.map +1 -1
- package/lib/components/QueryBuilderPropertyExpressionEditor.js +10 -26
- package/lib/components/QueryBuilderPropertyExpressionEditor.js.map +1 -1
- package/lib/components/QueryBuilderSideBar.d.ts.map +1 -1
- package/lib/components/QueryBuilderSideBar.js +3 -3
- package/lib/components/QueryBuilderSideBar.js.map +1 -1
- package/lib/components/QueryBuilderTextEditor.d.ts.map +1 -1
- package/lib/components/QueryBuilderTextEditor.js +17 -3
- package/lib/components/QueryBuilderTextEditor.js.map +1 -1
- package/lib/components/explorer/QueryBuilderMilestoningEditor.d.ts +5 -0
- package/lib/components/explorer/QueryBuilderMilestoningEditor.d.ts.map +1 -1
- package/lib/components/explorer/QueryBuilderMilestoningEditor.js +10 -5
- package/lib/components/explorer/QueryBuilderMilestoningEditor.js.map +1 -1
- package/lib/components/fetch-structure/QueryBuilderResultModifierPanel.d.ts.map +1 -1
- package/lib/components/fetch-structure/QueryBuilderResultModifierPanel.js +45 -12
- package/lib/components/fetch-structure/QueryBuilderResultModifierPanel.js.map +1 -1
- package/lib/components/fetch-structure/QueryBuilderTDSPanel.d.ts.map +1 -1
- package/lib/components/fetch-structure/QueryBuilderTDSPanel.js +13 -5
- package/lib/components/fetch-structure/QueryBuilderTDSPanel.js.map +1 -1
- package/lib/components/filter/QueryBuilderFilterPanel.d.ts.map +1 -1
- package/lib/components/filter/QueryBuilderFilterPanel.js +1 -2
- package/lib/components/filter/QueryBuilderFilterPanel.js.map +1 -1
- package/lib/components/result/QueryBuilderResultPanel.d.ts.map +1 -1
- package/lib/components/result/QueryBuilderResultPanel.js +6 -5
- package/lib/components/result/QueryBuilderResultPanel.js.map +1 -1
- package/lib/components/shared/BasicValueSpecificationEditor.d.ts.map +1 -1
- package/lib/components/shared/BasicValueSpecificationEditor.js +49 -8
- package/lib/components/shared/BasicValueSpecificationEditor.js.map +1 -1
- package/lib/components/workflows/ClassQueryBuilder.d.ts.map +1 -1
- package/lib/components/workflows/ClassQueryBuilder.js +3 -3
- package/lib/components/workflows/ClassQueryBuilder.js.map +1 -1
- package/lib/components/workflows/MappingQueryBuilder.d.ts.map +1 -1
- package/lib/components/workflows/MappingQueryBuilder.js +3 -3
- package/lib/components/workflows/MappingQueryBuilder.js.map +1 -1
- package/lib/components/workflows/ServiceQueryBuilder.d.ts.map +1 -1
- package/lib/components/workflows/ServiceQueryBuilder.js +3 -3
- package/lib/components/workflows/ServiceQueryBuilder.js.map +1 -1
- package/lib/index.css +2 -2
- package/lib/index.css.map +1 -1
- package/lib/package.json +1 -1
- package/lib/stores/QueryBuilderTextEditorState.d.ts +4 -1
- package/lib/stores/QueryBuilderTextEditorState.d.ts.map +1 -1
- package/lib/stores/QueryBuilderTextEditorState.js +19 -2
- package/lib/stores/QueryBuilderTextEditorState.js.map +1 -1
- package/lib/stores/QueryLoaderState.d.ts +2 -2
- package/lib/stores/QueryLoaderState.d.ts.map +1 -1
- package/lib/stores/QueryLoaderState.js +3 -3
- package/lib/stores/QueryLoaderState.js.map +1 -1
- package/lib/stores/explorer/QueryFunctionsExplorerState.d.ts +1 -1
- package/lib/stores/explorer/QueryFunctionsExplorerState.d.ts.map +1 -1
- package/lib/stores/explorer/QueryFunctionsExplorerState.js +2 -1
- package/lib/stores/explorer/QueryFunctionsExplorerState.js.map +1 -1
- package/lib/stores/fetch-structure/tds/QueryBuilderTDSState.d.ts +1 -0
- package/lib/stores/fetch-structure/tds/QueryBuilderTDSState.d.ts.map +1 -1
- package/lib/stores/fetch-structure/tds/QueryBuilderTDSState.js +8 -0
- package/lib/stores/fetch-structure/tds/QueryBuilderTDSState.js.map +1 -1
- package/lib/stores/milestoning/QueryBuilderMilestoningState.d.ts.map +1 -1
- package/lib/stores/milestoning/QueryBuilderMilestoningState.js +9 -3
- package/lib/stores/milestoning/QueryBuilderMilestoningState.js.map +1 -1
- package/lib/stores/watermark/QueryBuilderWatermarkState.d.ts.map +1 -1
- package/lib/stores/watermark/QueryBuilderWatermarkState.js +0 -1
- package/lib/stores/watermark/QueryBuilderWatermarkState.js.map +1 -1
- package/package.json +8 -8
- package/src/__lib__/QueryBuilderTesting.ts +1 -0
- package/src/components/QueryBuilder.tsx +16 -15
- package/src/components/QueryBuilderParametersPanel.tsx +2 -2
- package/src/components/QueryBuilderPropertyExpressionEditor.tsx +40 -92
- package/src/components/QueryBuilderSideBar.tsx +3 -2
- package/src/components/QueryBuilderTextEditor.tsx +46 -11
- package/src/components/explorer/QueryBuilderMilestoningEditor.tsx +60 -46
- package/src/components/fetch-structure/QueryBuilderResultModifierPanel.tsx +78 -34
- package/src/components/fetch-structure/QueryBuilderTDSPanel.tsx +121 -34
- package/src/components/filter/QueryBuilderFilterPanel.tsx +0 -11
- package/src/components/result/QueryBuilderResultPanel.tsx +21 -23
- package/src/components/shared/BasicValueSpecificationEditor.tsx +141 -34
- package/src/components/workflows/ClassQueryBuilder.tsx +3 -2
- package/src/components/workflows/MappingQueryBuilder.tsx +3 -2
- package/src/components/workflows/ServiceQueryBuilder.tsx +7 -3
- package/src/stores/QueryBuilderTextEditorState.ts +20 -2
- package/src/stores/QueryLoaderState.ts +5 -7
- package/src/stores/explorer/QueryFunctionsExplorerState.ts +6 -2
- package/src/stores/fetch-structure/tds/QueryBuilderTDSState.ts +11 -0
- package/src/stores/milestoning/QueryBuilderMilestoningState.ts +11 -7
- package/src/stores/watermark/QueryBuilderWatermarkState.ts +0 -1
|
@@ -16,7 +16,6 @@
|
|
|
16
16
|
|
|
17
17
|
import {
|
|
18
18
|
BlankPanelContent,
|
|
19
|
-
PanelLoadingIndicator,
|
|
20
19
|
PlayIcon,
|
|
21
20
|
DropdownMenu,
|
|
22
21
|
MenuContent,
|
|
@@ -43,6 +42,8 @@ import {
|
|
|
43
42
|
CsvIcon,
|
|
44
43
|
DebugIcon,
|
|
45
44
|
ReportIcon,
|
|
45
|
+
CubesLoadingIndicatorIcon,
|
|
46
|
+
CubesLoadingIndicator,
|
|
46
47
|
} from '@finos/legend-art';
|
|
47
48
|
import { observer } from 'mobx-react-lite';
|
|
48
49
|
import { flowResult } from 'mobx';
|
|
@@ -334,6 +335,9 @@ export const QueryBuilderResultPanel = observer(
|
|
|
334
335
|
</MenuContentItem>
|
|
335
336
|
));
|
|
336
337
|
|
|
338
|
+
const isLoading =
|
|
339
|
+
resultState.isRunningQuery || resultState.isGeneratingPlan;
|
|
340
|
+
|
|
337
341
|
return (
|
|
338
342
|
<div
|
|
339
343
|
data-testid={QUERY_BUILDER_TEST_ID.QUERY_BUILDER_RESULT_PANEL}
|
|
@@ -383,7 +387,7 @@ export const QueryBuilderResultPanel = observer(
|
|
|
383
387
|
|
|
384
388
|
<div className="panel__header">
|
|
385
389
|
<div className="panel__header__title">
|
|
386
|
-
<div className="panel__header__title__label">
|
|
390
|
+
<div className="panel__header__title__label">results</div>
|
|
387
391
|
{executedSql && (
|
|
388
392
|
<Button
|
|
389
393
|
onClick={() => setShowSqlModal(true)}
|
|
@@ -457,7 +461,7 @@ export const QueryBuilderResultPanel = observer(
|
|
|
457
461
|
{allowSettingPreviewLimit && (
|
|
458
462
|
<div className="query-builder__result__limit">
|
|
459
463
|
<div className="query-builder__result__limit__label">
|
|
460
|
-
preview limit
|
|
464
|
+
preview row limit
|
|
461
465
|
</div>
|
|
462
466
|
<input
|
|
463
467
|
ref={inputRef}
|
|
@@ -476,22 +480,20 @@ export const QueryBuilderResultPanel = observer(
|
|
|
476
480
|
<div className="query-builder__result__execute-btn btn__dropdown-combo btn__dropdown-combo--primary">
|
|
477
481
|
{resultState.isRunningQuery ? (
|
|
478
482
|
<button
|
|
479
|
-
className="btn__dropdown-combo__canceler"
|
|
483
|
+
className="btn__dropdown-combo__canceler query-builder__result__execute-btn__btn"
|
|
480
484
|
onClick={cancelQuery}
|
|
481
485
|
tabIndex={-1}
|
|
482
486
|
disabled={!isQueryValid}
|
|
483
487
|
>
|
|
484
|
-
<div className="btn--dark btn--caution btn__dropdown-combo__canceler__label">
|
|
485
|
-
<PauseCircleIcon
|
|
486
|
-
|
|
487
|
-
Stop
|
|
488
|
-
</div>
|
|
488
|
+
<div className="btn--dark btn--caution btn__dropdown-combo__canceler__label query-builder__result__execute-btn__btn">
|
|
489
|
+
<PauseCircleIcon />
|
|
490
|
+
Stop
|
|
489
491
|
</div>
|
|
490
492
|
</button>
|
|
491
493
|
) : (
|
|
492
494
|
<>
|
|
493
495
|
<button
|
|
494
|
-
className="btn__dropdown-combo__label"
|
|
496
|
+
className="btn__dropdown-combo__label query-builder__result__execute-btn__btn query-builder__result__execute-btn__btn--green"
|
|
495
497
|
onClick={runQuery}
|
|
496
498
|
tabIndex={-1}
|
|
497
499
|
title={
|
|
@@ -503,13 +505,11 @@ export const QueryBuilderResultPanel = observer(
|
|
|
503
505
|
}
|
|
504
506
|
disabled={isRunQueryDisabled}
|
|
505
507
|
>
|
|
506
|
-
<PlayIcon
|
|
507
|
-
|
|
508
|
-
Run Query
|
|
509
|
-
</div>
|
|
508
|
+
<PlayIcon />
|
|
509
|
+
Run Query
|
|
510
510
|
</button>
|
|
511
511
|
<DropdownMenu
|
|
512
|
-
className="btn__dropdown-combo__dropdown-btn"
|
|
512
|
+
className="btn__dropdown-combo__dropdown-btn query-builder__result__execute-btn__btn query-builder__result__execute-btn__btn--green"
|
|
513
513
|
disabled={isRunQueryDisabled}
|
|
514
514
|
content={
|
|
515
515
|
<MenuContent>
|
|
@@ -617,18 +617,16 @@ export const QueryBuilderResultPanel = observer(
|
|
|
617
617
|
))}
|
|
618
618
|
</div>
|
|
619
619
|
</div>
|
|
620
|
-
<PanelContent>
|
|
621
|
-
<
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
/>
|
|
626
|
-
{!executionResult && (
|
|
620
|
+
<PanelContent className="query-builder__result__content">
|
|
621
|
+
<CubesLoadingIndicator isLoading={isLoading}>
|
|
622
|
+
<CubesLoadingIndicatorIcon />
|
|
623
|
+
</CubesLoadingIndicator>
|
|
624
|
+
{!executionResult && !isLoading && (
|
|
627
625
|
<BlankPanelContent>
|
|
628
626
|
Build or load a valid query first
|
|
629
627
|
</BlankPanelContent>
|
|
630
628
|
)}
|
|
631
|
-
{executionResult && (
|
|
629
|
+
{executionResult && !isLoading && (
|
|
632
630
|
<div className="query-builder__result__values">
|
|
633
631
|
<QueryBuilderResultValues
|
|
634
632
|
executionResult={executionResult}
|
|
@@ -776,6 +776,98 @@ const setCollectionValue = (
|
|
|
776
776
|
instanceValue_setValues(valueSpecification, result, obseverContext);
|
|
777
777
|
};
|
|
778
778
|
|
|
779
|
+
const EnumCollectionInstanceValueEditor = observer(
|
|
780
|
+
(props: {
|
|
781
|
+
valueSpecification: CollectionInstanceValue;
|
|
782
|
+
observerContext: ObserverContext;
|
|
783
|
+
saveEdit: () => void;
|
|
784
|
+
}) => {
|
|
785
|
+
const { valueSpecification, observerContext, saveEdit } = props;
|
|
786
|
+
const applicationStore = useApplicationStore();
|
|
787
|
+
const enumType = guaranteeType(
|
|
788
|
+
valueSpecification.genericType?.value.rawType,
|
|
789
|
+
Enumeration,
|
|
790
|
+
);
|
|
791
|
+
|
|
792
|
+
const [selectedOptions, setSelectedOptions] = useState<
|
|
793
|
+
{ label: string; value: Enum }[]
|
|
794
|
+
>(
|
|
795
|
+
(valueSpecification.values as EnumValueInstanceValue[])
|
|
796
|
+
.filter((valueSpec) => valueSpec.values[0]?.value !== undefined)
|
|
797
|
+
.map((valueSpec) => ({
|
|
798
|
+
label: valueSpec.values[0]!.value.name,
|
|
799
|
+
value: valueSpec.values[0]!.value,
|
|
800
|
+
})),
|
|
801
|
+
);
|
|
802
|
+
|
|
803
|
+
const availableOptions = enumType.values
|
|
804
|
+
.filter(
|
|
805
|
+
(value) =>
|
|
806
|
+
!selectedOptions.some(
|
|
807
|
+
(selectedValue) => selectedValue.value.name === value.name,
|
|
808
|
+
),
|
|
809
|
+
)
|
|
810
|
+
.map((value) => ({
|
|
811
|
+
label: value.name,
|
|
812
|
+
value: value,
|
|
813
|
+
}));
|
|
814
|
+
|
|
815
|
+
const changeValue = (
|
|
816
|
+
newSelectedOptions: { value: Enum; label: string }[],
|
|
817
|
+
): void => {
|
|
818
|
+
setSelectedOptions(newSelectedOptions);
|
|
819
|
+
};
|
|
820
|
+
|
|
821
|
+
const updateValueSpecAndSaveEdit = (): void => {
|
|
822
|
+
const result = selectedOptions
|
|
823
|
+
.map((value) => {
|
|
824
|
+
const enumValueInstanceValue = new EnumValueInstanceValue(
|
|
825
|
+
GenericTypeExplicitReference.create(new GenericType(enumType)),
|
|
826
|
+
);
|
|
827
|
+
instanceValue_setValues(
|
|
828
|
+
enumValueInstanceValue,
|
|
829
|
+
[EnumValueExplicitReference.create(value.value)],
|
|
830
|
+
observerContext,
|
|
831
|
+
);
|
|
832
|
+
return enumValueInstanceValue;
|
|
833
|
+
})
|
|
834
|
+
.filter(isNonNullable);
|
|
835
|
+
instanceValue_setValues(valueSpecification, result, observerContext);
|
|
836
|
+
saveEdit();
|
|
837
|
+
};
|
|
838
|
+
|
|
839
|
+
return (
|
|
840
|
+
<>
|
|
841
|
+
<CustomSelectorInput
|
|
842
|
+
className="value-spec-editor__enum-collection-selector"
|
|
843
|
+
options={availableOptions}
|
|
844
|
+
isMulti={true}
|
|
845
|
+
onChange={changeValue}
|
|
846
|
+
onBlur={updateValueSpecAndSaveEdit}
|
|
847
|
+
onKeyDown={(event: KeyboardEvent): void => {
|
|
848
|
+
if (event.key === 'Enter' && !event.shiftKey) {
|
|
849
|
+
updateValueSpecAndSaveEdit();
|
|
850
|
+
}
|
|
851
|
+
}}
|
|
852
|
+
value={selectedOptions}
|
|
853
|
+
darkMode={
|
|
854
|
+
!applicationStore.layoutService.TEMPORARY__isLightColorThemeEnabled
|
|
855
|
+
}
|
|
856
|
+
placeholder="Select value"
|
|
857
|
+
autoFocus={true}
|
|
858
|
+
menuIsOpen={true}
|
|
859
|
+
/>
|
|
860
|
+
<button
|
|
861
|
+
className="value-spec-editor__list-editor__save-button btn--dark"
|
|
862
|
+
onClick={updateValueSpecAndSaveEdit}
|
|
863
|
+
>
|
|
864
|
+
<SaveIcon />
|
|
865
|
+
</button>
|
|
866
|
+
</>
|
|
867
|
+
);
|
|
868
|
+
},
|
|
869
|
+
);
|
|
870
|
+
|
|
779
871
|
const COLLECTION_PREVIEW_CHAR_LIMIT = 50;
|
|
780
872
|
|
|
781
873
|
const getPlaceHolder = (expectedType: Type): string => {
|
|
@@ -836,6 +928,11 @@ const CollectionValueInstanceValueEditor = observer(
|
|
|
836
928
|
if (editable) {
|
|
837
929
|
setEditable(false);
|
|
838
930
|
setShowAdvancedEditorPopover(false);
|
|
931
|
+
setValueSpecification(valueSpecification);
|
|
932
|
+
}
|
|
933
|
+
};
|
|
934
|
+
const updateValueSpecAndSaveEdit = (): void => {
|
|
935
|
+
if (editable) {
|
|
839
936
|
setCollectionValue(
|
|
840
937
|
valueSpecification,
|
|
841
938
|
expectedType,
|
|
@@ -843,7 +940,7 @@ const CollectionValueInstanceValueEditor = observer(
|
|
|
843
940
|
obseverContext,
|
|
844
941
|
);
|
|
845
942
|
setText(stringifyValue(valueSpecification.values));
|
|
846
|
-
|
|
943
|
+
saveEdit();
|
|
847
944
|
}
|
|
848
945
|
};
|
|
849
946
|
|
|
@@ -861,7 +958,7 @@ const CollectionValueInstanceValueEditor = observer(
|
|
|
861
958
|
(event.relatedTarget as HTMLButtonElement | undefined)?.name !==
|
|
862
959
|
expandButtonName
|
|
863
960
|
) {
|
|
864
|
-
|
|
961
|
+
updateValueSpecAndSaveEdit();
|
|
865
962
|
}
|
|
866
963
|
};
|
|
867
964
|
|
|
@@ -891,7 +988,7 @@ const CollectionValueInstanceValueEditor = observer(
|
|
|
891
988
|
onChange={changeValueTextArea}
|
|
892
989
|
onKeyDown={(event): void => {
|
|
893
990
|
if (event.key === 'Enter' && !event.shiftKey) {
|
|
894
|
-
|
|
991
|
+
updateValueSpecAndSaveEdit();
|
|
895
992
|
}
|
|
896
993
|
}}
|
|
897
994
|
/>
|
|
@@ -903,37 +1000,47 @@ const CollectionValueInstanceValueEditor = observer(
|
|
|
903
1000
|
</BasePopover>
|
|
904
1001
|
)}
|
|
905
1002
|
<div className={clsx('value-spec-editor', className)}>
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
917
|
-
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
|
|
1003
|
+
{expectedType instanceof Enumeration ? (
|
|
1004
|
+
<EnumCollectionInstanceValueEditor
|
|
1005
|
+
valueSpecification={valueSpecification}
|
|
1006
|
+
observerContext={obseverContext}
|
|
1007
|
+
saveEdit={saveEdit}
|
|
1008
|
+
/>
|
|
1009
|
+
) : (
|
|
1010
|
+
<>
|
|
1011
|
+
<textarea
|
|
1012
|
+
ref={inputRef}
|
|
1013
|
+
className={clsx(
|
|
1014
|
+
'panel__content__form__section__input value-spec-editor__input value-spec-editor__textarea ',
|
|
1015
|
+
)}
|
|
1016
|
+
spellCheck={false}
|
|
1017
|
+
value={text}
|
|
1018
|
+
placeholder={placeholder}
|
|
1019
|
+
onChange={changeValueTextArea}
|
|
1020
|
+
onKeyDown={(event): void => {
|
|
1021
|
+
if (event.key === 'Enter' && !event.shiftKey) {
|
|
1022
|
+
updateValueSpecAndSaveEdit();
|
|
1023
|
+
}
|
|
1024
|
+
}}
|
|
1025
|
+
onBlur={handleOnBlur}
|
|
1026
|
+
/>
|
|
1027
|
+
<button
|
|
1028
|
+
className="value-spec-editor__list-editor__expand-button btn--dark"
|
|
1029
|
+
onClick={() => setShowAdvancedEditorPopover(true)}
|
|
1030
|
+
tabIndex={-1}
|
|
1031
|
+
name={expandButtonName}
|
|
1032
|
+
title="Expand window..."
|
|
1033
|
+
>
|
|
1034
|
+
<FilledWindowMaximizeIcon />
|
|
1035
|
+
</button>
|
|
1036
|
+
<button
|
|
1037
|
+
className="value-spec-editor__list-editor__save-button btn--dark"
|
|
1038
|
+
onClick={saveEdit}
|
|
1039
|
+
>
|
|
1040
|
+
<SaveIcon />
|
|
1041
|
+
</button>
|
|
1042
|
+
</>
|
|
1043
|
+
)}
|
|
937
1044
|
<button
|
|
938
1045
|
className="value-spec-editor__reset-btn"
|
|
939
1046
|
name="Reset"
|
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
import {
|
|
18
18
|
CustomSelectorInput,
|
|
19
19
|
PanelHeader,
|
|
20
|
+
compareLabelFn,
|
|
20
21
|
createFilter,
|
|
21
22
|
} from '@finos/legend-art';
|
|
22
23
|
import { observer } from 'mobx-react-lite';
|
|
@@ -71,7 +72,7 @@ const ClassQueryBuilderSetupPanelContent = observer(
|
|
|
71
72
|
: []
|
|
72
73
|
)
|
|
73
74
|
.map(buildElementOption)
|
|
74
|
-
.sort(
|
|
75
|
+
.sort(compareLabelFn);
|
|
75
76
|
const selectedMappingOption = queryBuilderState.executionContextState
|
|
76
77
|
.mapping
|
|
77
78
|
? buildElementOption(queryBuilderState.executionContextState.mapping)
|
|
@@ -107,7 +108,7 @@ const ClassQueryBuilderSetupPanelContent = observer(
|
|
|
107
108
|
new RuntimePointer(PackageableElementExplicitReference.create(rt)),
|
|
108
109
|
)
|
|
109
110
|
.map(buildRuntimeValueOption)
|
|
110
|
-
.sort(
|
|
111
|
+
.sort(compareLabelFn);
|
|
111
112
|
const selectedRuntimeOption = queryBuilderState.executionContextState
|
|
112
113
|
.runtimeValue
|
|
113
114
|
? buildRuntimeValueOption(
|
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
import {
|
|
18
18
|
CustomSelectorInput,
|
|
19
19
|
PanelHeader,
|
|
20
|
+
compareLabelFn,
|
|
20
21
|
createFilter,
|
|
21
22
|
} from '@finos/legend-art';
|
|
22
23
|
import { observer } from 'mobx-react-lite';
|
|
@@ -59,7 +60,7 @@ const MappingQueryBuilderSetupPanelContent = observer(
|
|
|
59
60
|
// mapping
|
|
60
61
|
const mappingOptions = queryBuilderState.graphManagerState.usableMappings
|
|
61
62
|
.map(buildElementOption)
|
|
62
|
-
.sort(
|
|
63
|
+
.sort(compareLabelFn);
|
|
63
64
|
const selectedMappingOption = queryBuilderState.executionContextState
|
|
64
65
|
.mapping
|
|
65
66
|
? buildElementOption(queryBuilderState.executionContextState.mapping)
|
|
@@ -93,7 +94,7 @@ const MappingQueryBuilderSetupPanelContent = observer(
|
|
|
93
94
|
new RuntimePointer(PackageableElementExplicitReference.create(rt)),
|
|
94
95
|
)
|
|
95
96
|
.map(buildRuntimeValueOption)
|
|
96
|
-
.sort(
|
|
97
|
+
.sort(compareLabelFn);
|
|
97
98
|
const selectedRuntimeOption = queryBuilderState.executionContextState
|
|
98
99
|
.runtimeValue
|
|
99
100
|
? buildRuntimeValueOption(
|
|
@@ -14,7 +14,11 @@
|
|
|
14
14
|
* limitations under the License.
|
|
15
15
|
*/
|
|
16
16
|
|
|
17
|
-
import {
|
|
17
|
+
import {
|
|
18
|
+
CustomSelectorInput,
|
|
19
|
+
PanelHeader,
|
|
20
|
+
compareLabelFn,
|
|
21
|
+
} from '@finos/legend-art';
|
|
18
22
|
import { observer } from 'mobx-react-lite';
|
|
19
23
|
import { getMappingCompatibleClasses, type Service } from '@finos/legend-graph';
|
|
20
24
|
import { useApplicationStore } from '@finos/legend-application';
|
|
@@ -57,7 +61,7 @@ const ServiceQueryBuilderSetupPanelContent = observer(
|
|
|
57
61
|
const serviceOptions =
|
|
58
62
|
queryBuilderState.usableServices
|
|
59
63
|
?.map(buildElementOption)
|
|
60
|
-
.sort(
|
|
64
|
+
.sort(compareLabelFn) ?? [];
|
|
61
65
|
const selectedServiceOption = buildElementOption(queryBuilderState.service);
|
|
62
66
|
const onServiceOptionChange = (
|
|
63
67
|
option: PackageableElementOption<Service>,
|
|
@@ -71,7 +75,7 @@ const ServiceQueryBuilderSetupPanelContent = observer(
|
|
|
71
75
|
// execution context
|
|
72
76
|
const executionContextOptions = queryBuilderState.executionContexts
|
|
73
77
|
.map(buildExecutionContextOption)
|
|
74
|
-
.sort(
|
|
78
|
+
.sort(compareLabelFn);
|
|
75
79
|
const selectedExecutionContextOption =
|
|
76
80
|
queryBuilderState.selectedExecutionContext
|
|
77
81
|
? buildExecutionContextOption(
|
|
@@ -67,6 +67,7 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
67
67
|
* TODO: consider moving this to another state if we need to simplify the logic of text-mode
|
|
68
68
|
*/
|
|
69
69
|
readOnlylambdaJson = '';
|
|
70
|
+
isReadOnly: boolean | undefined;
|
|
70
71
|
|
|
71
72
|
constructor(queryBuilderState: QueryBuilderState) {
|
|
72
73
|
super('', '');
|
|
@@ -75,7 +76,9 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
75
76
|
rawLambdaState: observable,
|
|
76
77
|
isConvertingLambdaToString: observable,
|
|
77
78
|
mode: observable,
|
|
79
|
+
isReadOnly: observable,
|
|
78
80
|
setQueryRawLambdaState: action,
|
|
81
|
+
setIsReadOnly: action,
|
|
79
82
|
setMode: action,
|
|
80
83
|
openModal: action,
|
|
81
84
|
closeModal: flow,
|
|
@@ -89,10 +92,23 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
89
92
|
return buildSourceInformationSourceId(['query-builder']);
|
|
90
93
|
}
|
|
91
94
|
|
|
95
|
+
get text(): string | undefined {
|
|
96
|
+
if (this.mode === QueryBuilderTextEditorMode.TEXT) {
|
|
97
|
+
return this.fullLambdaString;
|
|
98
|
+
} else if (this.mode === QueryBuilderTextEditorMode.JSON) {
|
|
99
|
+
return this.readOnlylambdaJson;
|
|
100
|
+
}
|
|
101
|
+
return undefined;
|
|
102
|
+
}
|
|
103
|
+
|
|
92
104
|
setQueryRawLambdaState(rawLambdaState: QueryBuilderRawLambdaState): void {
|
|
93
105
|
this.rawLambdaState = rawLambdaState;
|
|
94
106
|
}
|
|
95
107
|
|
|
108
|
+
setIsReadOnly(val: boolean | undefined): void {
|
|
109
|
+
this.isReadOnly = val;
|
|
110
|
+
}
|
|
111
|
+
|
|
96
112
|
setMode(openModal: QueryBuilderTextEditorMode | undefined): void {
|
|
97
113
|
this.mode = openModal;
|
|
98
114
|
}
|
|
@@ -170,7 +186,7 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
170
186
|
}
|
|
171
187
|
}
|
|
172
188
|
|
|
173
|
-
openModal(mode: QueryBuilderTextEditorMode): void {
|
|
189
|
+
openModal(mode: QueryBuilderTextEditorMode, isReadOnly?: boolean): void {
|
|
174
190
|
try {
|
|
175
191
|
const rawLambda = this.queryBuilderState.buildQuery();
|
|
176
192
|
if (mode === QueryBuilderTextEditorMode.TEXT) {
|
|
@@ -190,6 +206,7 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
190
206
|
);
|
|
191
207
|
}
|
|
192
208
|
this.setMode(mode);
|
|
209
|
+
this.setIsReadOnly(isReadOnly);
|
|
193
210
|
} catch (error) {
|
|
194
211
|
assertErrorThrown(error);
|
|
195
212
|
this.queryBuilderState.applicationStore.notificationService.notifyError(
|
|
@@ -200,7 +217,7 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
200
217
|
|
|
201
218
|
*closeModal(): GeneratorFn<void> {
|
|
202
219
|
this.closingQueryState.inProgress();
|
|
203
|
-
if (this.mode === QueryBuilderTextEditorMode.TEXT) {
|
|
220
|
+
if (this.mode === QueryBuilderTextEditorMode.TEXT && !this.isReadOnly) {
|
|
204
221
|
yield flowResult(this.convertLambdaGrammarStringToObject());
|
|
205
222
|
if (this.parserError) {
|
|
206
223
|
this.queryBuilderState.applicationStore.notificationService.notifyError(
|
|
@@ -215,6 +232,7 @@ export class QueryBuilderTextEditorState extends LambdaEditorState {
|
|
|
215
232
|
}
|
|
216
233
|
return;
|
|
217
234
|
}
|
|
235
|
+
this.setIsReadOnly(undefined);
|
|
218
236
|
this.closingQueryState.complete();
|
|
219
237
|
|
|
220
238
|
this.setMode(undefined);
|
|
@@ -65,7 +65,7 @@ export class QueryLoaderState {
|
|
|
65
65
|
|
|
66
66
|
readonly isReadOnly?: boolean | undefined;
|
|
67
67
|
readonly onQueryRenamed?: ((query: LightQuery) => void) | undefined;
|
|
68
|
-
readonly onQueryDeleted?: ((query:
|
|
68
|
+
readonly onQueryDeleted?: ((query: string) => void) | undefined;
|
|
69
69
|
readonly handleFetchDefaultQueriesFailure?: (() => void) | undefined;
|
|
70
70
|
|
|
71
71
|
queryBuilderState?: QueryBuilderState | undefined;
|
|
@@ -100,7 +100,7 @@ export class QueryLoaderState {
|
|
|
100
100
|
|
|
101
101
|
isReadOnly?: boolean | undefined;
|
|
102
102
|
onQueryRenamed?: ((query: LightQuery) => void) | undefined;
|
|
103
|
-
onQueryDeleted?: ((query:
|
|
103
|
+
onQueryDeleted?: ((query: string) => void) | undefined;
|
|
104
104
|
handleFetchDefaultQueriesFailure?: (() => void) | undefined;
|
|
105
105
|
},
|
|
106
106
|
) {
|
|
@@ -304,11 +304,9 @@ export class QueryLoaderState {
|
|
|
304
304
|
*deleteQuery(queryId: string): GeneratorFn<void> {
|
|
305
305
|
this.deleteQueryState.inProgress();
|
|
306
306
|
try {
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
this.onQueryDeleted?.(query);
|
|
311
|
-
this.applicationStore.notificationService.notify(
|
|
307
|
+
yield this.graphManagerState.graphManager.deleteQuery(queryId);
|
|
308
|
+
this.onQueryDeleted?.(queryId);
|
|
309
|
+
this.applicationStore.notificationService.notifySuccess(
|
|
312
310
|
'Deleted query successfully',
|
|
313
311
|
);
|
|
314
312
|
this.deleteQueryState.pass();
|
|
@@ -30,7 +30,11 @@ import {
|
|
|
30
30
|
} from '@finos/legend-shared';
|
|
31
31
|
import { action, makeObservable, observable } from 'mobx';
|
|
32
32
|
import type { QueryBuilderState } from '../QueryBuilderState.js';
|
|
33
|
-
import
|
|
33
|
+
import {
|
|
34
|
+
type TreeNodeData,
|
|
35
|
+
type TreeData,
|
|
36
|
+
compareLabelFn,
|
|
37
|
+
} from '@finos/legend-art';
|
|
34
38
|
|
|
35
39
|
export const QUERY_BUILDER_FUNCTION_DND_TYPE = 'QUERY_BUILDER_FUNCTION';
|
|
36
40
|
|
|
@@ -206,7 +210,7 @@ export const getFunctionsExplorerTreeNodeChildren = (
|
|
|
206
210
|
return node.childrenIds
|
|
207
211
|
.map((id) => data.nodes.get(id))
|
|
208
212
|
.filter(isNonNullable)
|
|
209
|
-
.sort(
|
|
213
|
+
.sort(compareLabelFn)
|
|
210
214
|
.sort(
|
|
211
215
|
(a, b) =>
|
|
212
216
|
(b.packageableElement instanceof Package ? 1 : 0) -
|
|
@@ -146,6 +146,7 @@ export class QueryBuilderTDSState
|
|
|
146
146
|
TEMPORARY__showPostFetchStructurePanel: computed,
|
|
147
147
|
derivations: computed,
|
|
148
148
|
hasParserError: computed,
|
|
149
|
+
isQueryOptionsSet: computed,
|
|
149
150
|
addColumn: action,
|
|
150
151
|
moveColumn: action,
|
|
151
152
|
removeAllColumns: action,
|
|
@@ -356,6 +357,16 @@ export class QueryBuilderTDSState
|
|
|
356
357
|
return fetchStructureValidationIssues;
|
|
357
358
|
}
|
|
358
359
|
|
|
360
|
+
get isQueryOptionsSet(): boolean {
|
|
361
|
+
return (
|
|
362
|
+
this.resultSetModifierState.limit !== undefined ||
|
|
363
|
+
this.queryBuilderState.milestoningState.isMilestonedQuery ||
|
|
364
|
+
this.resultSetModifierState.slice !== undefined ||
|
|
365
|
+
this.resultSetModifierState.sortColumns.length > 0 ||
|
|
366
|
+
this.resultSetModifierState.distinct
|
|
367
|
+
);
|
|
368
|
+
}
|
|
369
|
+
|
|
359
370
|
get tdsColumns(): QueryBuilderTDSColumnState[] {
|
|
360
371
|
const aggregationStateCols = this.aggregationState.columns.map(
|
|
361
372
|
(c) => c.projectionColumnState,
|
|
@@ -75,7 +75,7 @@ export class QueryBuilderMilestoningState implements Hashable {
|
|
|
75
75
|
startDate: observable,
|
|
76
76
|
endDate: observable,
|
|
77
77
|
showMilestoningEditor: observable,
|
|
78
|
-
|
|
78
|
+
|
|
79
79
|
setProcessingDate: action,
|
|
80
80
|
setBusinessDate: action,
|
|
81
81
|
setStartDate: action,
|
|
@@ -87,6 +87,10 @@ export class QueryBuilderMilestoningState implements Hashable {
|
|
|
87
87
|
initializeAllVersionsInRangeParameters: action,
|
|
88
88
|
clearAllVersionsInRangeParameters: action,
|
|
89
89
|
clearGetAllParameters: action,
|
|
90
|
+
|
|
91
|
+
isAllVersionsEnabled: computed,
|
|
92
|
+
isAllVersionsInRangeEnabled: computed,
|
|
93
|
+
isMilestonedQuery: computed,
|
|
90
94
|
hashCode: computed,
|
|
91
95
|
});
|
|
92
96
|
|
|
@@ -380,9 +384,9 @@ export class QueryBuilderMilestoningState implements Hashable {
|
|
|
380
384
|
this.queryBuilderState.parametersState.parameterStates.find(
|
|
381
385
|
(p) => p.parameter === this.startDate,
|
|
382
386
|
);
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
387
|
+
if (paramState) {
|
|
388
|
+
this.queryBuilderState.parametersState.removeParameter(paramState);
|
|
389
|
+
}
|
|
386
390
|
}
|
|
387
391
|
if (
|
|
388
392
|
this.endDate instanceof VariableExpression &&
|
|
@@ -394,9 +398,9 @@ export class QueryBuilderMilestoningState implements Hashable {
|
|
|
394
398
|
this.queryBuilderState.parametersState.parameterStates.find(
|
|
395
399
|
(p) => p.parameter === this.endDate,
|
|
396
400
|
);
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
401
|
+
if (paramState) {
|
|
402
|
+
this.queryBuilderState.parametersState.removeParameter(paramState);
|
|
403
|
+
}
|
|
400
404
|
}
|
|
401
405
|
this.setStartDate(undefined);
|
|
402
406
|
this.setEndDate(undefined);
|