@quillsql/react 2.13.26 → 2.13.28
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/dist/cjs/Chart.d.ts.map +1 -1
- package/dist/cjs/Chart.js +2 -2
- package/dist/cjs/ChartBuilder.d.ts +20 -2
- package/dist/cjs/ChartBuilder.d.ts.map +1 -1
- package/dist/cjs/ChartBuilder.js +130 -36
- package/dist/cjs/ChartEditor.d.ts +5 -3
- package/dist/cjs/ChartEditor.d.ts.map +1 -1
- package/dist/cjs/ChartEditor.js +4 -5
- package/dist/cjs/Context.d.ts +15 -4
- package/dist/cjs/Context.d.ts.map +1 -1
- package/dist/cjs/Context.js +37 -60
- package/dist/cjs/Dashboard.d.ts +4 -0
- package/dist/cjs/Dashboard.d.ts.map +1 -1
- package/dist/cjs/Dashboard.js +78 -23
- package/dist/cjs/QuillProvider.d.ts +12 -9
- package/dist/cjs/QuillProvider.d.ts.map +1 -1
- package/dist/cjs/QuillProvider.js +2 -2
- package/dist/cjs/ReportBuilder.d.ts +9 -1
- package/dist/cjs/ReportBuilder.d.ts.map +1 -1
- package/dist/cjs/ReportBuilder.js +198 -80
- package/dist/cjs/SQLEditor.d.ts +5 -1
- package/dist/cjs/SQLEditor.d.ts.map +1 -1
- package/dist/cjs/SQLEditor.js +81 -18
- package/dist/cjs/Table.d.ts.map +1 -1
- package/dist/cjs/Table.js +5 -4
- package/dist/cjs/components/Chart/InternalChart.d.ts.map +1 -1
- package/dist/cjs/components/Chart/InternalChart.js +106 -27
- package/dist/cjs/components/Chart/PieChart.d.ts.map +1 -1
- package/dist/cjs/components/Chart/PieChart.js +10 -7
- package/dist/cjs/components/Dashboard/DashboardFilter.d.ts +3 -2
- package/dist/cjs/components/Dashboard/DashboardFilter.d.ts.map +1 -1
- package/dist/cjs/components/Dashboard/DashboardFilter.js +65 -65
- package/dist/cjs/components/Dashboard/DataLoader.d.ts.map +1 -1
- package/dist/cjs/components/Dashboard/DataLoader.js +81 -34
- package/dist/cjs/components/Dashboard/MetricComponent.js +3 -3
- package/dist/cjs/components/Dashboard/util.d.ts.map +1 -1
- package/dist/cjs/components/Dashboard/util.js +6 -2
- package/dist/cjs/components/QuillMultiSelectWithCombo.d.ts +1 -1
- package/dist/cjs/components/QuillMultiSelectWithCombo.d.ts.map +1 -1
- package/dist/cjs/components/QuillMultiSelectWithCombo.js +17 -18
- package/dist/cjs/components/QuillTable.d.ts.map +1 -1
- package/dist/cjs/components/QuillTable.js +9 -1
- package/dist/cjs/components/ReportBuilder/FilterModal.d.ts.map +1 -1
- package/dist/cjs/components/ReportBuilder/FilterModal.js +25 -3
- package/dist/cjs/components/ReportBuilder/FilterStack.d.ts +2 -1
- package/dist/cjs/components/ReportBuilder/FilterStack.d.ts.map +1 -1
- package/dist/cjs/components/ReportBuilder/FilterStack.js +2 -2
- package/dist/cjs/components/ReportBuilder/convert.d.ts +1 -0
- package/dist/cjs/components/ReportBuilder/convert.d.ts.map +1 -1
- package/dist/cjs/components/ReportBuilder/convert.js +54 -4
- package/dist/cjs/components/ReportBuilder/ui.d.ts +2 -1
- package/dist/cjs/components/ReportBuilder/ui.d.ts.map +1 -1
- package/dist/cjs/components/ReportBuilder/ui.js +3 -2
- package/dist/cjs/components/UiComponents.d.ts +1 -0
- package/dist/cjs/components/UiComponents.d.ts.map +1 -1
- package/dist/cjs/hooks/useAskQuill.d.ts +1 -1
- package/dist/cjs/hooks/useAskQuill.d.ts.map +1 -1
- package/dist/cjs/hooks/useAskQuill.js +6 -5
- package/dist/cjs/hooks/useAstToFilterTree.d.ts +2 -1
- package/dist/cjs/hooks/useAstToFilterTree.d.ts.map +1 -1
- package/dist/cjs/hooks/useAstToFilterTree.js +3 -3
- package/dist/cjs/hooks/useDashboard.d.ts +5 -2
- package/dist/cjs/hooks/useDashboard.d.ts.map +1 -1
- package/dist/cjs/hooks/useDashboard.js +21 -7
- package/dist/cjs/hooks/useExport.d.ts.map +1 -1
- package/dist/cjs/hooks/useExport.js +6 -4
- package/dist/cjs/index.d.ts +1 -1
- package/dist/cjs/index.d.ts.map +1 -1
- package/dist/cjs/internals/ReportBuilder/PivotModal.d.ts +8 -2
- package/dist/cjs/internals/ReportBuilder/PivotModal.d.ts.map +1 -1
- package/dist/cjs/internals/ReportBuilder/PivotModal.js +59 -30
- package/dist/cjs/models/Client.d.ts +22 -3
- package/dist/cjs/models/Client.d.ts.map +1 -1
- package/dist/cjs/models/Dashboard.d.ts +1 -0
- package/dist/cjs/models/Dashboard.d.ts.map +1 -1
- package/dist/cjs/models/Report.d.ts +4 -0
- package/dist/cjs/models/Report.d.ts.map +1 -1
- package/dist/cjs/utils/astFilterProcessing.d.ts +3 -2
- package/dist/cjs/utils/astFilterProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/astFilterProcessing.js +3323 -977
- package/dist/cjs/utils/astProcessing.d.ts +1 -1
- package/dist/cjs/utils/astProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/astProcessing.js +3 -2
- package/dist/cjs/utils/client.d.ts +4 -2
- package/dist/cjs/utils/client.d.ts.map +1 -1
- package/dist/cjs/utils/client.js +47 -1
- package/dist/cjs/utils/columnProcessing.d.ts +3 -0
- package/dist/cjs/utils/columnProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/columnProcessing.js +34 -1
- package/dist/cjs/utils/dashboard.d.ts +4 -3
- package/dist/cjs/utils/dashboard.d.ts.map +1 -1
- package/dist/cjs/utils/dashboard.js +10 -91
- package/dist/cjs/utils/dataFetcher.d.ts +3 -1
- package/dist/cjs/utils/dataFetcher.d.ts.map +1 -1
- package/dist/cjs/utils/dataFetcher.js +66 -30
- package/dist/cjs/utils/filterProcessing.d.ts +1 -1
- package/dist/cjs/utils/filterProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/filterProcessing.js +2 -0
- package/dist/cjs/utils/pivotConstructor.d.ts +4 -1
- package/dist/cjs/utils/pivotConstructor.d.ts.map +1 -1
- package/dist/cjs/utils/pivotConstructor.js +7 -7
- package/dist/cjs/utils/pivotProcessing.d.ts +4 -1
- package/dist/cjs/utils/pivotProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/pivotProcessing.js +27 -20
- package/dist/cjs/utils/queryConstructor.d.ts.map +1 -1
- package/dist/cjs/utils/queryConstructor.js +101 -85
- package/dist/cjs/utils/report.d.ts +17 -5
- package/dist/cjs/utils/report.d.ts.map +1 -1
- package/dist/cjs/utils/report.js +23 -23
- package/dist/cjs/utils/schema.d.ts.map +1 -1
- package/dist/cjs/utils/schema.js +21 -21
- package/dist/cjs/utils/tableProcessing.d.ts +37 -10
- package/dist/cjs/utils/tableProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/tableProcessing.js +45 -38
- package/dist/cjs/utils/tenants.d.ts +11 -0
- package/dist/cjs/utils/tenants.d.ts.map +1 -0
- package/dist/cjs/utils/tenants.js +13 -0
- package/dist/cjs/utils/textProcessing.d.ts +1 -0
- package/dist/cjs/utils/textProcessing.d.ts.map +1 -1
- package/dist/cjs/utils/textProcessing.js +49 -0
- package/dist/cjs/utils/validation.js +1 -1
- package/dist/esm/Chart.d.ts.map +1 -1
- package/dist/esm/Chart.js +2 -2
- package/dist/esm/ChartBuilder.d.ts +20 -2
- package/dist/esm/ChartBuilder.d.ts.map +1 -1
- package/dist/esm/ChartBuilder.js +131 -40
- package/dist/esm/ChartEditor.d.ts +5 -3
- package/dist/esm/ChartEditor.d.ts.map +1 -1
- package/dist/esm/ChartEditor.js +5 -6
- package/dist/esm/Context.d.ts +15 -4
- package/dist/esm/Context.d.ts.map +1 -1
- package/dist/esm/Context.js +36 -59
- package/dist/esm/Dashboard.d.ts +4 -0
- package/dist/esm/Dashboard.d.ts.map +1 -1
- package/dist/esm/Dashboard.js +79 -24
- package/dist/esm/QuillProvider.d.ts +12 -9
- package/dist/esm/QuillProvider.d.ts.map +1 -1
- package/dist/esm/QuillProvider.js +2 -2
- package/dist/esm/ReportBuilder.d.ts +9 -1
- package/dist/esm/ReportBuilder.d.ts.map +1 -1
- package/dist/esm/ReportBuilder.js +200 -84
- package/dist/esm/SQLEditor.d.ts +5 -1
- package/dist/esm/SQLEditor.d.ts.map +1 -1
- package/dist/esm/SQLEditor.js +80 -17
- package/dist/esm/Table.d.ts.map +1 -1
- package/dist/esm/Table.js +6 -5
- package/dist/esm/components/Chart/InternalChart.d.ts.map +1 -1
- package/dist/esm/components/Chart/InternalChart.js +107 -28
- package/dist/esm/components/Chart/PieChart.d.ts.map +1 -1
- package/dist/esm/components/Chart/PieChart.js +10 -7
- package/dist/esm/components/Dashboard/DashboardFilter.d.ts +3 -2
- package/dist/esm/components/Dashboard/DashboardFilter.d.ts.map +1 -1
- package/dist/esm/components/Dashboard/DashboardFilter.js +65 -65
- package/dist/esm/components/Dashboard/DataLoader.d.ts.map +1 -1
- package/dist/esm/components/Dashboard/DataLoader.js +82 -35
- package/dist/esm/components/Dashboard/MetricComponent.js +3 -3
- package/dist/esm/components/Dashboard/util.d.ts.map +1 -1
- package/dist/esm/components/Dashboard/util.js +6 -2
- package/dist/esm/components/QuillMultiSelectWithCombo.d.ts +1 -1
- package/dist/esm/components/QuillMultiSelectWithCombo.d.ts.map +1 -1
- package/dist/esm/components/QuillMultiSelectWithCombo.js +17 -18
- package/dist/esm/components/QuillTable.d.ts.map +1 -1
- package/dist/esm/components/QuillTable.js +9 -1
- package/dist/esm/components/ReportBuilder/FilterModal.d.ts.map +1 -1
- package/dist/esm/components/ReportBuilder/FilterModal.js +26 -4
- package/dist/esm/components/ReportBuilder/FilterStack.d.ts +2 -1
- package/dist/esm/components/ReportBuilder/FilterStack.d.ts.map +1 -1
- package/dist/esm/components/ReportBuilder/FilterStack.js +2 -2
- package/dist/esm/components/ReportBuilder/convert.d.ts +1 -0
- package/dist/esm/components/ReportBuilder/convert.d.ts.map +1 -1
- package/dist/esm/components/ReportBuilder/convert.js +54 -5
- package/dist/esm/components/ReportBuilder/ui.d.ts +2 -1
- package/dist/esm/components/ReportBuilder/ui.d.ts.map +1 -1
- package/dist/esm/components/ReportBuilder/ui.js +4 -3
- package/dist/esm/components/UiComponents.d.ts +1 -0
- package/dist/esm/components/UiComponents.d.ts.map +1 -1
- package/dist/esm/hooks/useAskQuill.d.ts +1 -1
- package/dist/esm/hooks/useAskQuill.d.ts.map +1 -1
- package/dist/esm/hooks/useAskQuill.js +7 -6
- package/dist/esm/hooks/useAstToFilterTree.d.ts +2 -1
- package/dist/esm/hooks/useAstToFilterTree.d.ts.map +1 -1
- package/dist/esm/hooks/useAstToFilterTree.js +3 -3
- package/dist/esm/hooks/useDashboard.d.ts +5 -2
- package/dist/esm/hooks/useDashboard.d.ts.map +1 -1
- package/dist/esm/hooks/useDashboard.js +21 -7
- package/dist/esm/hooks/useExport.d.ts.map +1 -1
- package/dist/esm/hooks/useExport.js +7 -5
- package/dist/esm/index.d.ts +1 -1
- package/dist/esm/index.d.ts.map +1 -1
- package/dist/esm/internals/ReportBuilder/PivotModal.d.ts +8 -2
- package/dist/esm/internals/ReportBuilder/PivotModal.d.ts.map +1 -1
- package/dist/esm/internals/ReportBuilder/PivotModal.js +59 -30
- package/dist/esm/models/Client.d.ts +22 -3
- package/dist/esm/models/Client.d.ts.map +1 -1
- package/dist/esm/models/Dashboard.d.ts +1 -0
- package/dist/esm/models/Dashboard.d.ts.map +1 -1
- package/dist/esm/models/Report.d.ts +4 -0
- package/dist/esm/models/Report.d.ts.map +1 -1
- package/dist/esm/utils/astFilterProcessing.d.ts +3 -2
- package/dist/esm/utils/astFilterProcessing.d.ts.map +1 -1
- package/dist/esm/utils/astFilterProcessing.js +3323 -977
- package/dist/esm/utils/astProcessing.d.ts +1 -1
- package/dist/esm/utils/astProcessing.d.ts.map +1 -1
- package/dist/esm/utils/astProcessing.js +4 -3
- package/dist/esm/utils/client.d.ts +4 -2
- package/dist/esm/utils/client.d.ts.map +1 -1
- package/dist/esm/utils/client.js +47 -1
- package/dist/esm/utils/columnProcessing.d.ts +3 -0
- package/dist/esm/utils/columnProcessing.d.ts.map +1 -1
- package/dist/esm/utils/columnProcessing.js +31 -1
- package/dist/esm/utils/dashboard.d.ts +4 -3
- package/dist/esm/utils/dashboard.d.ts.map +1 -1
- package/dist/esm/utils/dashboard.js +10 -90
- package/dist/esm/utils/dataFetcher.d.ts +3 -1
- package/dist/esm/utils/dataFetcher.d.ts.map +1 -1
- package/dist/esm/utils/dataFetcher.js +65 -29
- package/dist/esm/utils/filterProcessing.d.ts +1 -1
- package/dist/esm/utils/filterProcessing.d.ts.map +1 -1
- package/dist/esm/utils/filterProcessing.js +2 -0
- package/dist/esm/utils/pivotConstructor.d.ts +4 -1
- package/dist/esm/utils/pivotConstructor.d.ts.map +1 -1
- package/dist/esm/utils/pivotConstructor.js +8 -8
- package/dist/esm/utils/pivotProcessing.d.ts +4 -1
- package/dist/esm/utils/pivotProcessing.d.ts.map +1 -1
- package/dist/esm/utils/pivotProcessing.js +27 -20
- package/dist/esm/utils/queryConstructor.d.ts.map +1 -1
- package/dist/esm/utils/queryConstructor.js +101 -85
- package/dist/esm/utils/report.d.ts +17 -5
- package/dist/esm/utils/report.d.ts.map +1 -1
- package/dist/esm/utils/report.js +20 -23
- package/dist/esm/utils/schema.d.ts.map +1 -1
- package/dist/esm/utils/schema.js +21 -21
- package/dist/esm/utils/tableProcessing.d.ts +37 -10
- package/dist/esm/utils/tableProcessing.d.ts.map +1 -1
- package/dist/esm/utils/tableProcessing.js +46 -39
- package/dist/esm/utils/tenants.d.ts +11 -0
- package/dist/esm/utils/tenants.d.ts.map +1 -0
- package/dist/esm/utils/tenants.js +9 -0
- package/dist/esm/utils/textProcessing.d.ts +1 -0
- package/dist/esm/utils/textProcessing.d.ts.map +1 -1
- package/dist/esm/utils/textProcessing.js +48 -0
- package/dist/esm/utils/validation.js +1 -1
- package/package.json +1 -1
|
@@ -4,7 +4,7 @@ import { COMPARISON_OPTIONS, PRIMARY_RANGE, } from '../../DateRangePicker/dateRa
|
|
|
4
4
|
import { QuillDateRangePicker, } from '../../DateRangePicker/QuillDateRangePicker';
|
|
5
5
|
import { QuillMultiSelectComponent } from '../QuillMultiSelect';
|
|
6
6
|
import { QuillSelectComponent } from '../QuillSelect';
|
|
7
|
-
export function DashboardFilter({ filter, onChangeFilter, SelectComponent = QuillSelectComponent, MultiSelectComponent = QuillMultiSelectComponent, DateRangePickerComponent = QuillDateRangePicker, theme, isLoading, disabled, }) {
|
|
7
|
+
export function DashboardFilter({ filter, onChangeFilter, SelectComponent = QuillSelectComponent, MultiSelectComponent = QuillMultiSelectComponent, DateRangePickerComponent = QuillDateRangePicker, theme, isLoading, disabled, containerStyle, }) {
|
|
8
8
|
const preset = useMemo(() => {
|
|
9
9
|
if (('preset' in filter || 'primaryRange' in filter) &&
|
|
10
10
|
'startDate' in filter &&
|
|
@@ -24,79 +24,79 @@ export function DashboardFilter({ filter, onChangeFilter, SelectComponent = Quil
|
|
|
24
24
|
}
|
|
25
25
|
return '';
|
|
26
26
|
}, [filter]);
|
|
27
|
-
if (!filter.options && !isLoading && !(filter.filterType === 'date_range')) {
|
|
28
|
-
|
|
29
|
-
}
|
|
27
|
+
// if (!filter.options && !isLoading && !(filter.filterType === 'date_range')) {
|
|
28
|
+
// return null;
|
|
29
|
+
// }
|
|
30
30
|
if (filter.filterType === 'string') {
|
|
31
31
|
if (filter.stringFilterType === 'multiselect') {
|
|
32
|
-
return (_jsx(MultiSelectComponent, { label: filter.label, value: filter.values ?? [], onChange: (e) => {
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
32
|
+
return (_jsx("div", { style: containerStyle, children: _jsx(MultiSelectComponent, { label: filter.label, value: filter.values ?? [], onChange: (e) => {
|
|
33
|
+
if (e.target.value === '' ||
|
|
34
|
+
(Array.isArray(e.target.value) && e.target.value.length === 0)) {
|
|
35
|
+
onChangeFilter(filter, undefined);
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
let jsonValue = e.target.value;
|
|
39
|
+
if (typeof e.target.value === 'string') {
|
|
40
|
+
jsonValue = e.target.value.split(',');
|
|
41
|
+
}
|
|
42
|
+
onChangeFilter(filter, jsonValue);
|
|
43
|
+
}, options: [
|
|
44
|
+
...(filter.options
|
|
45
|
+
? filter.options.map((elem) => ({
|
|
46
|
+
label: elem[filter.labelField],
|
|
47
|
+
value: elem[filter.field],
|
|
48
|
+
}))
|
|
49
|
+
: []),
|
|
50
|
+
], width: 200, isLoading: isLoading, disabled: disabled }) }));
|
|
51
|
+
}
|
|
52
|
+
return (_jsx("div", { style: containerStyle, children: _jsx(SelectComponent, { label: filter.label, value: filter.selectedValue, onChange: (e) => {
|
|
53
|
+
onChangeFilter(filter, e.target.value);
|
|
43
54
|
}, options: [
|
|
44
55
|
...(filter.options
|
|
45
56
|
? filter.options.map((elem) => ({
|
|
46
|
-
label: elem[filter.labelField],
|
|
47
|
-
value: elem[filter.field],
|
|
57
|
+
label: elem[filter.labelField] ?? elem[filter.field] ?? '',
|
|
58
|
+
value: elem[filter.field] ?? '',
|
|
48
59
|
}))
|
|
49
60
|
: []),
|
|
50
|
-
], width: 200, isLoading: isLoading, disabled: disabled }));
|
|
51
|
-
}
|
|
52
|
-
return (_jsx(SelectComponent, { label: filter.label, value: filter.selectedValue, onChange: (e) => {
|
|
53
|
-
onChangeFilter(filter, e.target.value);
|
|
54
|
-
}, options: [
|
|
55
|
-
...(filter.options
|
|
56
|
-
? filter.options.map((elem) => ({
|
|
57
|
-
label: elem[filter.labelField] ?? elem[filter.field] ?? '',
|
|
58
|
-
value: elem[filter.field] ?? '',
|
|
59
|
-
}))
|
|
60
|
-
: []),
|
|
61
|
-
], width: 200, isLoading: isLoading, disabled: disabled }));
|
|
61
|
+
], width: 200, isLoading: isLoading, disabled: disabled }) }));
|
|
62
62
|
}
|
|
63
63
|
else if (filter.filterType === 'date_range') {
|
|
64
|
-
return (_jsxs("div", { style: {
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
64
|
+
return (_jsx("div", { style: containerStyle, children: _jsxs("div", { style: {
|
|
65
|
+
display: 'flex',
|
|
66
|
+
flexDirection: 'row',
|
|
67
|
+
alignItems: 'flex-end',
|
|
68
|
+
flexWrap: 'wrap',
|
|
69
|
+
}, children: [_jsx(DateRangePickerComponent, { label: filter.label, dateRange: { startDate: filter.startDate, endDate: filter.endDate }, preset: preset, onChangeDateRange: (value) => {
|
|
70
|
+
onChangeFilter(filter, {
|
|
71
|
+
startDate: value.startDate,
|
|
72
|
+
endDate: value.endDate,
|
|
73
|
+
});
|
|
74
|
+
}, onChangePreset: (e) => {
|
|
75
|
+
onChangeFilter(filter, { preset: e.target.value });
|
|
76
|
+
}, presetOptions: filter.options?.map((option) => {
|
|
77
|
+
return { label: option.label, value: option.value };
|
|
78
|
+
}) ?? [], selectWidth: 200, disabled: disabled }), filter.comparison && (_jsxs("div", { style: {
|
|
79
|
+
display: 'flex',
|
|
80
|
+
flexDirection: 'row',
|
|
81
|
+
alignItems: 'center',
|
|
82
|
+
}, children: [_jsx("div", { style: {
|
|
83
|
+
paddingLeft: 16,
|
|
84
|
+
paddingRight: 12,
|
|
85
|
+
color: theme?.secondaryTextColor,
|
|
86
|
+
fontFamily: theme?.fontFamily,
|
|
87
|
+
fontSize: 14,
|
|
88
|
+
display: 'flex',
|
|
89
|
+
alignItems: 'center',
|
|
90
|
+
flex: 1,
|
|
91
|
+
whiteSpace: 'nowrap',
|
|
92
|
+
minWidth: 80,
|
|
93
|
+
justifyContent: 'center',
|
|
94
|
+
}, children: "compared to" }), _jsx(SelectComponent, { value: filter.comparisonRange?.value ?? 'NO_COMPARISON', onChange: (e) => {
|
|
95
|
+
onChangeFilter(filter, undefined, COMPARISON_OPTIONS.find((option) => option.value === e.target.value));
|
|
96
|
+
}, options: COMPARISON_OPTIONS.map((compareOption) => ({
|
|
97
|
+
value: compareOption.value,
|
|
98
|
+
label: compareOption.text,
|
|
99
|
+
})), width: 200, hideEmptyOption: true })] }))] }) }));
|
|
100
100
|
}
|
|
101
101
|
return null;
|
|
102
102
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"DataLoader.d.ts","sourceRoot":"","sources":["../../../../src/components/Dashboard/DataLoader.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"DataLoader.d.ts","sourceRoot":"","sources":["../../../../src/components/Dashboard/DataLoader.tsx"],"names":[],"mappings":"AAUA,OAAO,EAAE,WAAW,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AACvE,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAajD,OAAO,EACL,oBAAoB,EAErB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AA0BtE,MAAM,MAAM,oBAAoB,GAAG;IACjC,SAAS,EAAE,OAAO,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACrC,YAAY,EAAE,CAAC,IAAI,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,KAAK,IAAI,CAAC;IACnE,IAAI,EAAE,WAAW,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,iBAAiB,CAAC,EAAE,OAAO,CAAC;CAC7B,CAAC;AAsJF,MAAM,CAAC,OAAO,UAAU,UAAU,CAAC,EACjC,IAAI,EACJ,QAAQ,EACR,OAAO,EACP,WAAW,EACX,oBAAoB,EAAE,2BAA2B,EACjD,UAAkB,GACnB,EAAE;IACD,IAAI,EAAE,mBAAmB,CAAC;IAC1B,OAAO,EAAE,eAAe,EAAE,CAAC;IAC3B,WAAW,CAAC,EAAE,cAAc,EAAE,CAAC;IAC/B,oBAAoB,EAAE,oBAAoB,CAAC;IAC3C,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,QAAQ,EAAE,CAAC,EACT,SAAS,EACT,KAAK,EACL,YAAY,EACZ,YAAY,EACZ,IAAI,GACL,EAAE,oBAAoB,KAAK,GAAG,CAAC,OAAO,CAAC;CACzC,GAAG,GAAG,CAAC,OAAO,CAgVd;AAED,KAAK,YAAY,GAAG;IAClB,CAAC,GAAG,EAAE,MAAM,GAAG;QACb,OAAO,EAAE,MAAM,CAAC;QAChB,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,oBAAoB,CAAC,EAAE,MAAM,CAAC;QAC9B,mBAAmB,CAAC,EAAE,MAAM,CAAC;QAC7B,uBAAuB,CAAC,EAAE,MAAM,CAAC;QACjC,sBAAsB,CAAC,EAAE,MAAM,CAAC;KACjC,CAAC;CACH,CAAC;AAEF,MAAM,MAAM,yBAAyB,GAAG;IACtC,SAAS,EAAE,OAAO,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,IAAI,EAAE,WAAW,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,iBAAiB,CAAC,EAAE,OAAO,CAAC;CAC7B,CAAC;AAIF,eAAO,MAAM,eAAe,4FAQzB;IACD,IAAI,EAAE,mBAAmB,CAAC;IAC1B,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,iBAAiB,CAAC,EAAE,CAClB,OAAO,EAAE,WAAW,EACpB,MAAM,EAAE,UAAU,KACf,YAAY,CAAC;IAClB,oBAAoB,EAAE,oBAAoB,CAAC;IAC3C,OAAO,EAAE,eAAe,EAAE,CAAC;IAC3B,WAAW,CAAC,EAAE,cAAc,EAAE,CAAC;IAC/B,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,QAAQ,EAAE,CAAC,EACT,SAAS,EACT,KAAK,EACL,IAAI,EACJ,UAAU,EACV,QAAQ,EACR,iBAAiB,GAClB,EAAE,yBAAyB,KAAK,GAAG,CAAC,OAAO,CAAC;CAC9C,KAAG,GAAG,CAAC,OAmKP,CAAC"}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { Fragment as _Fragment, jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { useContext, useEffect, useMemo, useRef, useState } from 'react';
|
|
3
|
-
import { ClientContext, DashboardContext, DashboardFiltersContext, ReportFiltersContext, ReportsContext, SchemaDataContext, } from '../../Context';
|
|
3
|
+
import { ClientContext, DashboardContext, DashboardFiltersContext, ReportFiltersContext, ReportsContext, SchemaDataContext, TenantContext, } from '../../Context';
|
|
4
4
|
import { convertInternalReportToReport, EMPTY_INTERNAL_REPORT, fetchReport, fetchReportRowCount, } from '../../utils/report';
|
|
5
5
|
import { shouldFetchMore, DEFAULT_PAGINATION, shouldSortInMemory, } from '../../utils/paginationProcessing';
|
|
6
6
|
import { fetchResultsByReport, } from '../../utils/tableProcessing';
|
|
7
|
-
import { didFiltersChange } from '../../Chart';
|
|
7
|
+
// import { didFiltersChange } from '../../Chart';
|
|
8
8
|
import { mergeComparisonRange } from '../../utils/merge';
|
|
9
9
|
import equal from 'fast-deep-equal';
|
|
10
10
|
const constructReportFromItem = (item) => {
|
|
@@ -87,10 +87,47 @@ function userFilterValuesEquivalent(filters1, filters2) {
|
|
|
87
87
|
}
|
|
88
88
|
return true;
|
|
89
89
|
}
|
|
90
|
+
function tenantsEquivalent(tenants1, tenants2) {
|
|
91
|
+
if (!tenants1 && !tenants2) {
|
|
92
|
+
return true;
|
|
93
|
+
}
|
|
94
|
+
if (tenants1?.length !== tenants2?.length) {
|
|
95
|
+
return false;
|
|
96
|
+
}
|
|
97
|
+
if (!tenants1 || !tenants2) {
|
|
98
|
+
return false;
|
|
99
|
+
}
|
|
100
|
+
// The two tenant arrays aren't necessarily in the same order
|
|
101
|
+
// we can build two dictionaries of [foreignKey, tenantIds] and compare them
|
|
102
|
+
// if they are arrays of strings or numbers, we can just compare them directly
|
|
103
|
+
if ((typeof tenants1[0] === 'string' && typeof tenants2[0] === 'string') ||
|
|
104
|
+
(typeof tenants1[0] === 'number' && typeof tenants2[0] === 'number')) {
|
|
105
|
+
return equal(tenants1, tenants2);
|
|
106
|
+
}
|
|
107
|
+
if ((typeof tenants1[0] === 'string' && typeof tenants2[0] !== 'string') ||
|
|
108
|
+
(typeof tenants1[0] === 'number' && typeof tenants2[0] !== 'number')) {
|
|
109
|
+
return false;
|
|
110
|
+
}
|
|
111
|
+
const mappedTenants1 = tenants1.reduce((acc, tenant) => {
|
|
112
|
+
acc[tenant.tenantField] = tenant.tenantIds;
|
|
113
|
+
return acc;
|
|
114
|
+
}, {});
|
|
115
|
+
const mappedTenants2 = tenants2.reduce((acc, tenant) => {
|
|
116
|
+
acc[tenant.tenantField] = tenant.tenantIds;
|
|
117
|
+
return acc;
|
|
118
|
+
}, {});
|
|
119
|
+
for (const key in mappedTenants1) {
|
|
120
|
+
if (!equal(mappedTenants1[key], mappedTenants2[key])) {
|
|
121
|
+
return false;
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
return true;
|
|
125
|
+
}
|
|
90
126
|
export default function DataLoader({ item, children, filters, userFilters, additionalProcessing: defaultAdditionalProcessing, reportMode = false, }) {
|
|
91
127
|
const [client] = useContext(ClientContext);
|
|
92
128
|
const [dashboard, dispatch] = useContext(DashboardContext);
|
|
93
129
|
const { dashboardFilters } = useContext(DashboardFiltersContext);
|
|
130
|
+
const { tenants, flags } = useContext(TenantContext);
|
|
94
131
|
const { reports, reportsDispatch, fetchIndividualReport } = useContext(ReportsContext);
|
|
95
132
|
const { reportFilters } = useContext(ReportFiltersContext);
|
|
96
133
|
const contextFilters = () => {
|
|
@@ -99,7 +136,7 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
99
136
|
: Object.values(dashboardFilters[item.dashboardName] ?? {}).map((f) => f.filter);
|
|
100
137
|
};
|
|
101
138
|
const [schemaData] = useContext(SchemaDataContext);
|
|
102
|
-
const [loading, setLoading] = useState(
|
|
139
|
+
const [loading, setLoading] = useState(true);
|
|
103
140
|
const [error, setError] = useState(undefined);
|
|
104
141
|
const [previousPage, setPreviousPage] = useState(0);
|
|
105
142
|
const [additionalProcessing, setAdditionalProcessing] = useState(defaultAdditionalProcessing);
|
|
@@ -116,6 +153,7 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
116
153
|
reportFilters,
|
|
117
154
|
dashboardFilters,
|
|
118
155
|
]);
|
|
156
|
+
const previousTenants = useRef(null);
|
|
119
157
|
const previousFilters = useRef(null);
|
|
120
158
|
const previousUserFilters = useRef(null);
|
|
121
159
|
const [rowCountIsLoading, setRowCountIsLoading] = useState(false);
|
|
@@ -127,6 +165,8 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
127
165
|
const updateTableRowsAbortController = useRef(null);
|
|
128
166
|
const fetchRowCount = async (processing) => {
|
|
129
167
|
if (!client || !filters) {
|
|
168
|
+
if (!rowCountAbortController.current)
|
|
169
|
+
return;
|
|
130
170
|
return;
|
|
131
171
|
}
|
|
132
172
|
const fetchReportRowCountRequestId = rowCountRequestId.current + 1;
|
|
@@ -135,7 +175,7 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
135
175
|
rowCountAbortController.current?.abort();
|
|
136
176
|
rowCountAbortController.current = new AbortController();
|
|
137
177
|
try {
|
|
138
|
-
const rowCount = await fetchReportRowCount(item.id, client, true, filters.concat(userFilters ?? []), processing, schemaData.customFields, rowCountAbortController.current.signal);
|
|
178
|
+
const rowCount = await fetchReportRowCount(item.id, client, tenants, flags, true, filters.concat(userFilters ?? []), processing, schemaData.customFields, rowCountAbortController.current.signal);
|
|
139
179
|
rowCountAbortController.current = null;
|
|
140
180
|
if (rowCount) {
|
|
141
181
|
if (reportMode) {
|
|
@@ -161,6 +201,7 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
161
201
|
}
|
|
162
202
|
finally {
|
|
163
203
|
if (fetchReportRowCountRequestId === rowCountRequestId.current) {
|
|
204
|
+
rowCountAbortController.current = null;
|
|
164
205
|
setRowCountIsLoading(false);
|
|
165
206
|
}
|
|
166
207
|
}
|
|
@@ -183,16 +224,21 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
183
224
|
};
|
|
184
225
|
const onSortChange = (sort) => {
|
|
185
226
|
const report = (reportMode ? reports : dashboard)[item.id];
|
|
186
|
-
if (shouldSortInMemory(additionalProcessing.page ?? DEFAULT_PAGINATION, report?.rowCount)
|
|
227
|
+
if (shouldSortInMemory(additionalProcessing.page ?? DEFAULT_PAGINATION, report?.rowCount) ||
|
|
228
|
+
report?.pivot) {
|
|
187
229
|
return;
|
|
188
230
|
}
|
|
189
|
-
const updatedProcessing = {
|
|
190
|
-
|
|
231
|
+
const updatedProcessing = {
|
|
232
|
+
page: { ...additionalProcessing.page, page: 0 },
|
|
233
|
+
sort,
|
|
234
|
+
};
|
|
191
235
|
updateTableRows(updatedProcessing, true);
|
|
192
236
|
setPreviousPage(0);
|
|
193
237
|
};
|
|
194
238
|
const updateTableRows = async (processing, resetRows = false) => {
|
|
195
239
|
if (!client) {
|
|
240
|
+
if (!updateTableRowsAbortController.current)
|
|
241
|
+
setLoading(false);
|
|
196
242
|
return;
|
|
197
243
|
}
|
|
198
244
|
if (!loading) {
|
|
@@ -203,7 +249,7 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
203
249
|
updateTableRowsAbortController.current?.abort();
|
|
204
250
|
updateTableRowsAbortController.current = new AbortController();
|
|
205
251
|
const updatedProcessing = { ...additionalProcessing, ...processing };
|
|
206
|
-
const paginatedRows = await fetchResultsByReport(item.id, client, updatedProcessing, filters.concat(userFilters ?? []), schemaData.customFields, true, undefined, updateTableRowsAbortController.current.signal);
|
|
252
|
+
const paginatedRows = await fetchResultsByReport(item.id, client, tenants, updatedProcessing, filters.concat(userFilters ?? []), schemaData.customFields, true, undefined, updateTableRowsAbortController.current.signal);
|
|
207
253
|
updateTableRowsAbortController.current = null;
|
|
208
254
|
if (paginatedRows.error) {
|
|
209
255
|
throw new Error('Error fetching chart');
|
|
@@ -244,6 +290,7 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
244
290
|
}
|
|
245
291
|
finally {
|
|
246
292
|
if (fetchUpdateTableRowsRequestId === updateTableRowsRequestId.current) {
|
|
293
|
+
updateTableRowsAbortController.current = null;
|
|
247
294
|
setLoading(false);
|
|
248
295
|
}
|
|
249
296
|
}
|
|
@@ -251,13 +298,8 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
251
298
|
};
|
|
252
299
|
const fetchReportHelper = async (processing) => {
|
|
253
300
|
if (!client || !filters) {
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
const tempReport = (reportMode ? reports : dashboard)[item.id];
|
|
257
|
-
if (tempReport &&
|
|
258
|
-
!didFiltersChange(tempReport, filters) &&
|
|
259
|
-
userFilterValuesEquivalent(userFilters ?? [], previousUserFilters.current ?? []) &&
|
|
260
|
-
!tempReport.triggerReload) {
|
|
301
|
+
if (!rowsAbortController.current)
|
|
302
|
+
setLoading(false);
|
|
261
303
|
return;
|
|
262
304
|
}
|
|
263
305
|
setLoading(true);
|
|
@@ -276,11 +318,9 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
276
318
|
catch (e) {
|
|
277
319
|
setError(e.message ?? 'Error fetching report');
|
|
278
320
|
}
|
|
279
|
-
rowsAbortController.current = null;
|
|
280
321
|
}
|
|
281
322
|
else {
|
|
282
|
-
const { report: fetchedReport, error } = await fetchReport(item.id, client, true, filters.concat(userFilters ?? []), processing, undefined, schemaData.customFields, true, false, rowsAbortController.current.signal);
|
|
283
|
-
rowsAbortController.current = null;
|
|
323
|
+
const { report: fetchedReport, error } = await fetchReport(item.id, client, tenants, flags, true, filters.concat(userFilters ?? []), processing, undefined, schemaData.customFields, true, false, rowsAbortController.current.signal);
|
|
284
324
|
dispatch({
|
|
285
325
|
type: 'ADD_DASHBOARD_ITEM',
|
|
286
326
|
id: item.id,
|
|
@@ -305,25 +345,31 @@ export default function DataLoader({ item, children, filters, userFilters, addit
|
|
|
305
345
|
}
|
|
306
346
|
finally {
|
|
307
347
|
if (fetchRowsRequestId === rowsRequestId.current) {
|
|
348
|
+
rowsAbortController.current = null;
|
|
308
349
|
setLoading(false);
|
|
309
350
|
}
|
|
310
351
|
}
|
|
311
352
|
};
|
|
353
|
+
// TODO: this is getting ridiculous
|
|
354
|
+
// we should be fetching this data directly when mutating filters/tenants rather than using a magical effect
|
|
312
355
|
useEffect(() => {
|
|
313
|
-
if (!filters) {
|
|
314
|
-
return;
|
|
315
|
-
}
|
|
316
356
|
if ((previousFilters.current ||
|
|
317
357
|
(reportMode ? reports : dashboard)[item.id]?.rows?.length) &&
|
|
318
358
|
filterValuesEquivalent(previousFilters.current ?? contextFilters(), filters) &&
|
|
319
|
-
userFilterValuesEquivalent(previousUserFilters.current ?? [], userFilters ?? [])
|
|
359
|
+
userFilterValuesEquivalent(previousUserFilters.current ?? [], userFilters ?? []) &&
|
|
360
|
+
// !didFiltersChange(dashboard[item.id], filters) &&
|
|
361
|
+
tenantsEquivalent(previousTenants.current ?? [], tenants ?? [])) {
|
|
362
|
+
if (!rowsAbortController.current)
|
|
363
|
+
setLoading(false);
|
|
320
364
|
previousFilters.current = filters;
|
|
321
365
|
return;
|
|
322
366
|
}
|
|
323
367
|
previousFilters.current = filters;
|
|
368
|
+
previousUserFilters.current = userFilters ?? [];
|
|
369
|
+
previousTenants.current = tenants ?? null;
|
|
324
370
|
setPreviousPage(0);
|
|
325
371
|
fetchReportHelper(additionalProcessing);
|
|
326
|
-
}, [filters, userFilters, item.id]);
|
|
372
|
+
}, [filters, userFilters, item.id, tenants]);
|
|
327
373
|
useEffect(() => {
|
|
328
374
|
const tempReport = (reportMode ? reports : dashboard)[item.id];
|
|
329
375
|
if (tempReport?.triggerReload) {
|
|
@@ -350,18 +396,20 @@ export const ChartDataLoader = ({ item, children, dateBucket, additionalProcessi
|
|
|
350
396
|
const { dashboardFilters } = useContext(DashboardFiltersContext);
|
|
351
397
|
const { reports, fetchIndividualReport } = useContext(ReportsContext);
|
|
352
398
|
const { reportFilters } = useContext(ReportFiltersContext);
|
|
399
|
+
const { tenants, flags } = useContext(TenantContext);
|
|
353
400
|
const contextFilters = () => {
|
|
354
401
|
return reportMode
|
|
355
402
|
? Object.values(reportFilters[item.id] ?? {}).map((f) => f.filter)
|
|
356
403
|
: Object.values(dashboardFilters[item.dashboardName] ?? {}).map((f) => f.filter);
|
|
357
404
|
};
|
|
358
|
-
const [loading, setLoading] = useState(
|
|
405
|
+
const [loading, setLoading] = useState(true);
|
|
359
406
|
const [error, setError] = useState(undefined);
|
|
360
407
|
const [client] = useContext(ClientContext);
|
|
361
408
|
const [schemaData] = useContext(SchemaDataContext);
|
|
362
409
|
const previousFilters = useRef(null);
|
|
363
410
|
const previousUserFilters = useRef(null);
|
|
364
411
|
const previousDateBucket = useRef(undefined);
|
|
412
|
+
const previousTenants = useRef(null);
|
|
365
413
|
const fetchReportAbortController = useRef(null);
|
|
366
414
|
const rowsRequestId = useRef(0);
|
|
367
415
|
const chartReport = useMemo(() => {
|
|
@@ -377,14 +425,8 @@ export const ChartDataLoader = ({ item, children, dateBucket, additionalProcessi
|
|
|
377
425
|
]);
|
|
378
426
|
const fetchReportHelper = async (useReportTask = true) => {
|
|
379
427
|
if (!client || !filters) {
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
const tempReport = (reportMode ? reports : dashboard)[item.id];
|
|
383
|
-
if (tempReport &&
|
|
384
|
-
!didFiltersChange(tempReport, filters) &&
|
|
385
|
-
userFilterValuesEquivalent(userFilters ?? [], previousUserFilters.current ?? []) &&
|
|
386
|
-
dateBucket === previousDateBucket.current &&
|
|
387
|
-
!tempReport.triggerReload) {
|
|
428
|
+
if (!fetchReportAbortController.current)
|
|
429
|
+
setLoading(false);
|
|
388
430
|
return;
|
|
389
431
|
}
|
|
390
432
|
const fetchRowsRequestId = rowsRequestId.current + 1;
|
|
@@ -406,14 +448,12 @@ export const ChartDataLoader = ({ item, children, dateBucket, additionalProcessi
|
|
|
406
448
|
catch (e) {
|
|
407
449
|
setError(e.message ?? 'Error fetching report');
|
|
408
450
|
}
|
|
409
|
-
fetchReportAbortController.current = null;
|
|
410
451
|
}
|
|
411
452
|
else {
|
|
412
|
-
const { report, error } = await fetchReport(item.id, client, useReportTask, filters.concat(userFilters ?? []), {
|
|
453
|
+
const { report, error } = await fetchReport(item.id, client, tenants, flags, useReportTask, filters.concat(userFilters ?? []), {
|
|
413
454
|
...additionalProcessing,
|
|
414
455
|
...(item.pivot ? {} : { page: DEFAULT_PAGINATION }),
|
|
415
456
|
}, dateBucket, schemaData.customFields, undefined, undefined, fetchReportAbortController.current.signal);
|
|
416
|
-
fetchReportAbortController.current = null;
|
|
417
457
|
dispatch({
|
|
418
458
|
type: 'ADD_DASHBOARD_ITEM',
|
|
419
459
|
id: item.id,
|
|
@@ -435,6 +475,7 @@ export const ChartDataLoader = ({ item, children, dateBucket, additionalProcessi
|
|
|
435
475
|
}
|
|
436
476
|
finally {
|
|
437
477
|
if (fetchRowsRequestId === rowsRequestId.current) {
|
|
478
|
+
fetchReportAbortController.current = null;
|
|
438
479
|
setLoading(false);
|
|
439
480
|
}
|
|
440
481
|
}
|
|
@@ -447,10 +488,16 @@ export const ChartDataLoader = ({ item, children, dateBucket, additionalProcessi
|
|
|
447
488
|
(reportMode ? reports : dashboard)[item.id]?.rows?.length) &&
|
|
448
489
|
filterValuesEquivalent(previousFilters.current ?? contextFilters(), filters) &&
|
|
449
490
|
userFilterValuesEquivalent(previousUserFilters.current ?? [], userFilters ?? []) &&
|
|
491
|
+
tenantsEquivalent(tenants ?? [], previousTenants.current ?? []) &&
|
|
450
492
|
previousDateBucket.current === dateBucket) {
|
|
451
493
|
previousFilters.current = filters;
|
|
494
|
+
if (!fetchReportAbortController.current)
|
|
495
|
+
setLoading(false);
|
|
452
496
|
return;
|
|
453
497
|
}
|
|
498
|
+
previousDateBucket.current = dateBucket;
|
|
499
|
+
previousUserFilters.current = userFilters ?? [];
|
|
500
|
+
previousTenants.current = tenants ?? null;
|
|
454
501
|
previousFilters.current = filters;
|
|
455
502
|
fetchReportHelper();
|
|
456
503
|
}, [filters, userFilters, item.id, dateBucket]);
|
|
@@ -62,7 +62,7 @@ export default function QuillMetricComponent({ report, onClick, error, isLoading
|
|
|
62
62
|
color: theme?.secondaryTextColor,
|
|
63
63
|
maxWidth: '100%',
|
|
64
64
|
width: '100%',
|
|
65
|
-
} })) : report
|
|
65
|
+
} })) : !report?.rows?.[0] ||
|
|
66
66
|
report.rows[0][report.xAxisField] === null ? (_jsx("div", { style: {
|
|
67
67
|
display: 'flex',
|
|
68
68
|
flex: '1 0 auto',
|
|
@@ -100,7 +100,7 @@ export default function QuillMetricComponent({ report, onClick, error, isLoading
|
|
|
100
100
|
gap: 4,
|
|
101
101
|
alignItems: 'baseline',
|
|
102
102
|
marginRight: 'auto',
|
|
103
|
-
}, children: [_jsx("span", { children: (report
|
|
103
|
+
}, children: [_jsx("span", { children: (report?.rows?.[0] &&
|
|
104
104
|
report.rows[0][report.xAxisField]) ??
|
|
105
105
|
0 }), dateFilter?.comparison && (_jsx("span", { style: {
|
|
106
106
|
fontSize: 13,
|
|
@@ -121,7 +121,7 @@ export default function QuillMetricComponent({ report, onClick, error, isLoading
|
|
|
121
121
|
fontWeight: '500',
|
|
122
122
|
fontFamily: theme?.fontFamily,
|
|
123
123
|
color: theme?.secondaryTextColor,
|
|
124
|
-
}, children: (report
|
|
124
|
+
}, children: (report?.rows?.[0] &&
|
|
125
125
|
report.rows[0][`comparison_${report.xAxisField}`]) ??
|
|
126
126
|
0 }), _jsx("span", { style: {
|
|
127
127
|
fontSize: 13,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"util.d.ts","sourceRoot":"","sources":["../../../../src/components/Dashboard/util.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;
|
|
1
|
+
{"version":3,"file":"util.d.ts","sourceRoot":"","sources":["../../../../src/components/Dashboard/util.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAK1D,wBAAgB,+BAA+B,CAC7C,OAAO,EAAE,GAAG,EAAE,EACd,SAAS,EAAE,GAAG,EAAE,GACf;IAAE,KAAK,EAAE,OAAO,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,CAiCnC;AAED,wBAAsB,uBAAuB,CAC3C,IAAI,EAAE,GAAG,EACT,YAAY,EAAE,GAAG,EAAE,EACnB,MAAM,EAAE,mBAAmB,EAC3B,aAAa,EAAE,GAAG,GACjB,OAAO,CAAC,GAAG,CAAC,CAmDd"}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { getData } from '../../utils/dataFetcher';
|
|
2
|
+
// WARNING: all of this template code is stale and PROBABLY BROKEN
|
|
2
3
|
export function validateTemplatesAgainstFilters(filters, templates) {
|
|
3
4
|
let error = '';
|
|
4
5
|
filters.every((filter) => {
|
|
@@ -36,13 +37,16 @@ export function validateTemplatesAgainstFilters(filters, templates) {
|
|
|
36
37
|
}
|
|
37
38
|
export async function addTemplatesToDashboard(name, newTemplates, client, dashboardData) {
|
|
38
39
|
try {
|
|
39
|
-
const { publicKey,
|
|
40
|
+
const { publicKey, tenants } = client;
|
|
41
|
+
if (tenants) {
|
|
42
|
+
// need to implement a way to specify report tenant id
|
|
43
|
+
throw new Error('Adding from template not yet supported for tenants');
|
|
44
|
+
}
|
|
40
45
|
const hostedBody = {
|
|
41
46
|
metadata: {
|
|
42
47
|
dashboardName: name,
|
|
43
48
|
task: 'add-from-template',
|
|
44
49
|
clientId: publicKey,
|
|
45
|
-
orgId: organizationId || '*',
|
|
46
50
|
templateReportIds: newTemplates.map((template) => template._id),
|
|
47
51
|
},
|
|
48
52
|
};
|
|
@@ -2,7 +2,7 @@ import { MultiSelectComponentProps } from './UiComponents';
|
|
|
2
2
|
/**
|
|
3
3
|
* A robust select component that implements the new minimal Select interface.
|
|
4
4
|
*/
|
|
5
|
-
export declare function QuillMultiSelectComponentWithCombo({ options, width, onChange, label, value, isLoading, disabled, }: MultiSelectComponentProps): import("react/jsx-runtime").JSX.Element;
|
|
5
|
+
export declare function QuillMultiSelectComponentWithCombo({ options, width, onChange, label, value, isLoading, disabled, emptyLabel, }: MultiSelectComponentProps): import("react/jsx-runtime").JSX.Element;
|
|
6
6
|
export declare const ListboxTextInput: ({ value, onChange, placeholder, }: {
|
|
7
7
|
value: string;
|
|
8
8
|
onChange: (e: string) => void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"QuillMultiSelectWithCombo.d.ts","sourceRoot":"","sources":["../../../src/components/QuillMultiSelectWithCombo.tsx"],"names":[],"mappings":"AACA,OAAO,EAAkB,yBAAyB,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"QuillMultiSelectWithCombo.d.ts","sourceRoot":"","sources":["../../../src/components/QuillMultiSelectWithCombo.tsx"],"names":[],"mappings":"AACA,OAAO,EAAkB,yBAAyB,EAAE,MAAM,gBAAgB,CAAC;AAW3E;;GAEG;AACH,wBAAgB,kCAAkC,CAAC,EACjD,OAAO,EACP,KAAK,EACL,QAAQ,EACR,KAAK,EACL,KAAK,EACL,SAAS,EACT,QAAQ,EACR,UAAU,GACX,EAAE,yBAAyB,2CAif3B;AAED,eAAO,MAAM,gBAAgB,sCAI1B;IACD,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,CAAC,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;IAC9B,WAAW,EAAE,MAAM,CAAC;CACrB,4CAwDA,CAAC"}
|
|
@@ -3,25 +3,10 @@ import { useOnClickOutside } from '../hooks';
|
|
|
3
3
|
import { LoadingSpinner } from './UiComponents';
|
|
4
4
|
import React, { useContext, useEffect, useMemo, useRef, useState, } from 'react';
|
|
5
5
|
import { ThemeContext } from '../Context';
|
|
6
|
-
/**
|
|
7
|
-
* Helper function for displaying option labels
|
|
8
|
-
*/
|
|
9
|
-
function displaySelectedOptionLabels({ options, value, }) {
|
|
10
|
-
if (!value || !value.length) {
|
|
11
|
-
return 'Select';
|
|
12
|
-
}
|
|
13
|
-
const matchingOptions = options.filter((elem) => value.includes(elem.value));
|
|
14
|
-
if (matchingOptions.length !== value.length) {
|
|
15
|
-
return value.join(', ');
|
|
16
|
-
}
|
|
17
|
-
return matchingOptions
|
|
18
|
-
.map((elem) => elem.label ?? '-')
|
|
19
|
-
.join(', ');
|
|
20
|
-
}
|
|
21
6
|
/**
|
|
22
7
|
* A robust select component that implements the new minimal Select interface.
|
|
23
8
|
*/
|
|
24
|
-
export function QuillMultiSelectComponentWithCombo({ options, width, onChange, label, value, isLoading, disabled, }) {
|
|
9
|
+
export function QuillMultiSelectComponentWithCombo({ options, width, onChange, label, value, isLoading, disabled, emptyLabel, }) {
|
|
25
10
|
const [theme] = useContext(ThemeContext);
|
|
26
11
|
const [selectedOptions, setSelectedOptions] = useState([]);
|
|
27
12
|
const [showModal, setShowModal] = useState(false);
|
|
@@ -47,6 +32,18 @@ export function QuillMultiSelectComponentWithCombo({ options, width, onChange, l
|
|
|
47
32
|
}))
|
|
48
33
|
.concat(options);
|
|
49
34
|
}, [value, options]);
|
|
35
|
+
const selectedOptionsLabel = useMemo(() => {
|
|
36
|
+
if (!value || !value.length) {
|
|
37
|
+
return 'Select';
|
|
38
|
+
}
|
|
39
|
+
const matchingOptions = options.filter((elem) => value.includes(elem.value));
|
|
40
|
+
if (matchingOptions.length !== value.length) {
|
|
41
|
+
return value.join(', ');
|
|
42
|
+
}
|
|
43
|
+
return matchingOptions
|
|
44
|
+
.map((elem) => elem.label ?? '-')
|
|
45
|
+
.join(', ');
|
|
46
|
+
}, [options, value]);
|
|
50
47
|
const [selectAllCheckboxState, setSelectAllCheckboxState] = useState((() => {
|
|
51
48
|
if (value.length === 0) {
|
|
52
49
|
return CheckboxState.UNSELECTED;
|
|
@@ -177,7 +174,7 @@ export function QuillMultiSelectComponentWithCombo({ options, width, onChange, l
|
|
|
177
174
|
width: '100%',
|
|
178
175
|
textAlign: 'left',
|
|
179
176
|
zIndex: 1,
|
|
180
|
-
}, children:
|
|
177
|
+
}, children: selectedOptionsLabel }), _jsx("svg", { xmlns: "http://www.w3.org/2000/svg", viewBox: "0 0 20 20", fill: "currentColor", "aria-hidden": "true", "data-slot": "icon", height: 20, width: 20, style: { minHeight: 20, minWidth: 20 }, children: _jsx("path", { fillRule: "evenodd", d: "M5.22 8.22a.75.75 0 0 1 1.06 0L10 11.94l3.72-3.72a.75.75 0 1 1 1.06 1.06l-4.25 4.25a.75.75 0 0 1-1.06 0L5.22 9.28a.75.75 0 0 1 0-1.06Z", clipRule: "evenodd" }) })] }), showModal && (_jsxs("div", { style: {
|
|
181
178
|
position: 'absolute',
|
|
182
179
|
width: '100%',
|
|
183
180
|
display: 'flex',
|
|
@@ -232,7 +229,9 @@ export function QuillMultiSelectComponentWithCombo({ options, width, onChange, l
|
|
|
232
229
|
whiteSpace: 'nowrap',
|
|
233
230
|
overflow: 'hidden',
|
|
234
231
|
cursor: 'default',
|
|
235
|
-
}, children: exceedsLimit
|
|
232
|
+
}, children: exceedsLimit
|
|
233
|
+
? 'Too many options'
|
|
234
|
+
: (emptyLabel ?? 'No options available') })] })), !exceedsLimit && !isLoading ? (_jsxs(_Fragment, { children: [searchQuery === '' && potentialOptions.length > 0 && (_jsxs("button", { style: {
|
|
236
235
|
display: 'flex',
|
|
237
236
|
alignItems: 'center',
|
|
238
237
|
padding: 8,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"QuillTable.d.ts","sourceRoot":"","sources":["../../../src/components/QuillTable.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA0C,MAAM,OAAO,CAAC;AAG/D,OAAO,EAAE,oBAAoB,EAAyB,MAAM,gBAAgB,CAAC;AAE7E,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B,OAAO,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,EAAE,CAAC;IAC5C,WAAW,EAAE,MAAM,CAAC;IACpB,IAAI,CAAC,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5C,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,KAAK,CAAC,aAAa,CAAC;IACrC,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,qBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,WAAW,CAAC,EAAE,MAAM,IAAI,CAAC;IACzB,gBAAgB,CAAC,EAAE,MAAM,GAAG,CAAC,OAAO,CAAC;IACrC,0BAA0B,CAAC,EAAE,CAAC,KAAK,EAAE,oBAAoB,KAAK,GAAG,CAAC,OAAO,CAAC;IAC1E,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACtC,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,KAAK,IAAI,CAAC;CACrE;AAED,UAAU,wBAAyB,SAAQ,mBAAmB;IAC5D,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED,MAAM,CAAC,OAAO,UAAU,UAAU,CAAC,EACjC,IAAI,EACJ,QAAQ,EACR,iBAAiB,EACjB,OAAO,EACP,SAAS,EACT,WAAW,EACX,IAAI,EACJ,qBAA4B,EAC5B,cAAc,EACd,SAAS,EACT,gBAAwC,EACxC,WAAgB,EAChB,eAA8B,EAC9B,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,UAAU,EACV,WAAW,GACZ,EAAE,wBAAwB,
|
|
1
|
+
{"version":3,"file":"QuillTable.d.ts","sourceRoot":"","sources":["../../../src/components/QuillTable.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA0C,MAAM,OAAO,CAAC;AAG/D,OAAO,EAAE,oBAAoB,EAAyB,MAAM,gBAAgB,CAAC;AAE7E,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B,OAAO,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,EAAE,CAAC;IAC5C,WAAW,EAAE,MAAM,CAAC;IACpB,IAAI,CAAC,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5C,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,KAAK,CAAC,aAAa,CAAC;IACrC,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,qBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,WAAW,CAAC,EAAE,MAAM,IAAI,CAAC;IACzB,gBAAgB,CAAC,EAAE,MAAM,GAAG,CAAC,OAAO,CAAC;IACrC,0BAA0B,CAAC,EAAE,CAAC,KAAK,EAAE,oBAAoB,KAAK,GAAG,CAAC,OAAO,CAAC;IAC1E,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACtC,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,KAAK,IAAI,CAAC;CACrE;AAED,UAAU,wBAAyB,SAAQ,mBAAmB;IAC5D,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED,MAAM,CAAC,OAAO,UAAU,UAAU,CAAC,EACjC,IAAI,EACJ,QAAQ,EACR,iBAAiB,EACjB,OAAO,EACP,SAAS,EACT,WAAW,EACX,IAAI,EACJ,qBAA4B,EAC5B,cAAc,EACd,SAAS,EACT,gBAAwC,EACxC,WAAgB,EAChB,eAA8B,EAC9B,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,UAAU,EACV,WAAW,GACZ,EAAE,wBAAwB,2CA8e1B"}
|
|
@@ -39,7 +39,15 @@ export default function QuillTable({ rows, rowCount, rowCountIsLoading, columns,
|
|
|
39
39
|
}
|
|
40
40
|
setIsPaginating(false);
|
|
41
41
|
setInitialLoad(false);
|
|
42
|
-
}, [
|
|
42
|
+
}, [
|
|
43
|
+
currentPage,
|
|
44
|
+
rows,
|
|
45
|
+
sortColumn,
|
|
46
|
+
sortDirection,
|
|
47
|
+
columns,
|
|
48
|
+
rowCount,
|
|
49
|
+
isLoading,
|
|
50
|
+
]);
|
|
43
51
|
useEffect(() => {
|
|
44
52
|
if (rows.length <= currentPage * rowsPerPage) {
|
|
45
53
|
onPageChange && onPageChange(0);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FilterModal.d.ts","sourceRoot":"","sources":["../../../../src/components/ReportBuilder/FilterModal.tsx"],"names":[],"mappings":"AAIA,OAAO,EACL,cAAc,EAId,QAAQ,EAMT,MAAM,qBAAqB,CAAC;AAM7B,OAAO,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AACtD,UAAU,gBAAgB;IACxB,MAAM,CAAC,EAAE;QAAE,OAAO,EAAE,cAAc,EAAE,CAAA;KAAE,CAAC;IACvC,MAAM,CAAC,EAAE,cAAc,CAAC;IACxB,cAAc,EACZ;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAAA;KAAE,GACzB;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG;YAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAAA;SAAE,CAAA;KAAE,CAAC;IACnD,uBAAuB,CAAC,EAAE,OAAO,CAAC;IAClC,qBAAqB,CAAC,EAAE,kBAAkB,CAAC;IAC3C,cAAc,EAAE,CAAC,MAAM,EAAE,cAAc,KAAK,IAAI,CAAC;IACjD,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B,eAAe,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IAC1C,eAAe,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IAC1C,kBAAkB,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IAC7C,wBAAwB,CAAC,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IACpD,oBAAoB,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;CAChD;AAQD,KAAK,kBAAkB,GAAG;IACxB,CAAC,GAAG,EAAE,MAAM,GAAG,QAAQ,EAAE,CAAC;CAC3B,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,OAAO,UAAU,WAAW,CAAC,EAClC,MAAM,EACN,MAAM,EACN,cAAc,EACd,uBAAuB,EACvB,qBAAqB,EACrB,cAAc,EACd,cAAc,EACd,eAAe,EACf,eAAe,EACf,kBAAkB,EAClB,wBAAwB,EACxB,oBAAoB,GACrB,EAAE,gBAAgB,
|
|
1
|
+
{"version":3,"file":"FilterModal.d.ts","sourceRoot":"","sources":["../../../../src/components/ReportBuilder/FilterModal.tsx"],"names":[],"mappings":"AAIA,OAAO,EACL,cAAc,EAId,QAAQ,EAMT,MAAM,qBAAqB,CAAC;AAM7B,OAAO,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AACtD,UAAU,gBAAgB;IACxB,MAAM,CAAC,EAAE;QAAE,OAAO,EAAE,cAAc,EAAE,CAAA;KAAE,CAAC;IACvC,MAAM,CAAC,EAAE,cAAc,CAAC;IACxB,cAAc,EACZ;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAAA;KAAE,GACzB;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG;YAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CAAA;SAAE,CAAA;KAAE,CAAC;IACnD,uBAAuB,CAAC,EAAE,OAAO,CAAC;IAClC,qBAAqB,CAAC,EAAE,kBAAkB,CAAC;IAC3C,cAAc,EAAE,CAAC,MAAM,EAAE,cAAc,KAAK,IAAI,CAAC;IACjD,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B,eAAe,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IAC1C,eAAe,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IAC1C,kBAAkB,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IAC7C,wBAAwB,CAAC,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;IACpD,oBAAoB,EAAE,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;CAChD;AAQD,KAAK,kBAAkB,GAAG;IACxB,CAAC,GAAG,EAAE,MAAM,GAAG,QAAQ,EAAE,CAAC;CAC3B,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,OAAO,UAAU,WAAW,CAAC,EAClC,MAAM,EACN,MAAM,EACN,cAAc,EACd,uBAAuB,EACvB,qBAAqB,EACrB,cAAc,EACd,cAAc,EACd,eAAe,EACf,eAAe,EACf,kBAAkB,EAClB,wBAAwB,EACxB,oBAAoB,GACrB,EAAE,gBAAgB,kDAi3BlB"}
|