mirror of https://github.com/buster-so/buster.git
update update functions
This commit is contained in:
parent
b7db8dc1ee
commit
9bc97db50c
|
@ -0,0 +1,118 @@
|
||||||
|
import { addAndRemoveMetricsToDashboard } from './addAndRemoveMetricsToDashboard';
|
||||||
|
import type { BusterDashboard } from '@/api/asset_interfaces/dashboard';
|
||||||
|
|
||||||
|
describe('addAndRemoveMetricsToDashboard', () => {
|
||||||
|
const createMockConfig = (metricIds: string[]): BusterDashboard['config'] => ({
|
||||||
|
rows: [
|
||||||
|
{
|
||||||
|
id: 'row-1',
|
||||||
|
items: metricIds.map((id) => ({ id })),
|
||||||
|
columnSizes: Array(metricIds.length).fill(12 / metricIds.length),
|
||||||
|
rowHeight: 320
|
||||||
|
}
|
||||||
|
]
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should return existing config when no changes are needed', () => {
|
||||||
|
const existingConfig = createMockConfig(['metric-1', 'metric-2']);
|
||||||
|
const result = addAndRemoveMetricsToDashboard(['metric-1', 'metric-2'], existingConfig);
|
||||||
|
expect(result).toEqual(existingConfig);
|
||||||
|
// Verify order is maintained
|
||||||
|
expect(result.rows?.[0].items.map((item) => item.id)).toEqual(['metric-1', 'metric-2']);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should add new metrics when they dont exist in the dashboard', () => {
|
||||||
|
const existingConfig = createMockConfig(['metric-1']);
|
||||||
|
const result = addAndRemoveMetricsToDashboard(
|
||||||
|
['metric-1', 'metric-2', 'metric-3'],
|
||||||
|
existingConfig
|
||||||
|
);
|
||||||
|
|
||||||
|
// Verify metrics were added in the correct order
|
||||||
|
const resultMetricIds = result.rows?.[0].items.map((item) => item.id);
|
||||||
|
expect(result.rows?.[0].items.map((item) => item.id)).toEqual(['metric-1']);
|
||||||
|
expect(result.rows?.[1].items.map((item) => item.id)).toEqual(['metric-2', 'metric-3']);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove metrics that are not in the provided array while maintaining order', () => {
|
||||||
|
const existingConfig = createMockConfig(['metric-1', 'metric-2', 'metric-3']);
|
||||||
|
const result = addAndRemoveMetricsToDashboard(['metric-1', 'metric-3'], existingConfig);
|
||||||
|
|
||||||
|
// Verify metric was removed while maintaining order of remaining metrics
|
||||||
|
const resultMetricIds = result.rows?.[0].items.map((item) => item.id);
|
||||||
|
expect(resultMetricIds).toEqual(['metric-1', 'metric-3']);
|
||||||
|
expect(resultMetricIds?.length).toBe(2);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle both adding and removing metrics simultaneously while maintaining order', () => {
|
||||||
|
const existingConfig = createMockConfig(['metric-1', 'metric-2', 'metric-3']);
|
||||||
|
const result = addAndRemoveMetricsToDashboard(
|
||||||
|
['metric-1', 'metric-4', 'metric-5'],
|
||||||
|
existingConfig
|
||||||
|
);
|
||||||
|
|
||||||
|
// Verify correct metrics were added and removed in the right order
|
||||||
|
expect(result.rows?.[0].items.map((item) => item.id)).toEqual(['metric-1']); // Order should match input array
|
||||||
|
expect(result.rows?.[1].items.map((item) => item.id)).toEqual(['metric-4', 'metric-5']); // Order should match input array
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle empty input array by removing all metrics', () => {
|
||||||
|
const existingConfig = createMockConfig(['metric-1', 'metric-2']);
|
||||||
|
const result = addAndRemoveMetricsToDashboard([], existingConfig);
|
||||||
|
|
||||||
|
// Verify all metrics were removed
|
||||||
|
expect(result.rows?.length).toBe(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle empty existing config by adding all metrics in order', () => {
|
||||||
|
const emptyConfig: BusterDashboard['config'] = { rows: [] };
|
||||||
|
const result = addAndRemoveMetricsToDashboard(['metric-1', 'metric-2'], emptyConfig);
|
||||||
|
|
||||||
|
// Verify all metrics were added in the correct order
|
||||||
|
const resultMetricIds = result.rows?.[0].items.map((item) => item.id);
|
||||||
|
expect(resultMetricIds).toEqual(['metric-1', 'metric-2']);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should maintain correct column sizes and order when removing metrics', () => {
|
||||||
|
const existingConfig = createMockConfig(['metric-1', 'metric-2', 'metric-3']);
|
||||||
|
const result = addAndRemoveMetricsToDashboard(['metric-1', 'metric-3'], existingConfig);
|
||||||
|
|
||||||
|
// Verify column sizes are updated correctly while maintaining order
|
||||||
|
expect(result.rows?.[0].columnSizes).toEqual([6, 6]); // 12/2 = 6 for each column
|
||||||
|
expect(result.rows?.[0].items.map((item) => item.id)).toEqual(['metric-1', 'metric-3']);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle multiple rows and maintain order within each row', () => {
|
||||||
|
const existingConfig: BusterDashboard['config'] = {
|
||||||
|
rows: [
|
||||||
|
{
|
||||||
|
id: 'row-1',
|
||||||
|
items: [{ id: 'metric-1' }, { id: 'metric-2' }],
|
||||||
|
columnSizes: [6, 6],
|
||||||
|
rowHeight: 320
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 'row-2',
|
||||||
|
items: [{ id: 'metric-3' }, { id: 'metric-4' }],
|
||||||
|
columnSizes: [6, 6],
|
||||||
|
rowHeight: 320
|
||||||
|
}
|
||||||
|
]
|
||||||
|
};
|
||||||
|
|
||||||
|
const result = addAndRemoveMetricsToDashboard(
|
||||||
|
['metric-1', 'metric-3', 'metric-5'],
|
||||||
|
existingConfig
|
||||||
|
);
|
||||||
|
|
||||||
|
// Verify order is maintained in each row after modifications
|
||||||
|
expect(result.rows?.[0].items.map((item) => item.id)).toEqual(['metric-1']);
|
||||||
|
expect(result.rows?.[0].columnSizes).toEqual([12]);
|
||||||
|
|
||||||
|
expect(result.rows?.[1].items.map((item) => item.id)).toEqual(['metric-3']);
|
||||||
|
expect(result.rows?.[1].columnSizes).toEqual([12]);
|
||||||
|
|
||||||
|
expect(result.rows?.[2].items.map((item) => item.id)).toEqual(['metric-5']);
|
||||||
|
expect(result.rows?.[2].columnSizes).toEqual([12]);
|
||||||
|
});
|
||||||
|
});
|
|
@ -0,0 +1,36 @@
|
||||||
|
import type { BusterDashboard } from '@/api/asset_interfaces/dashboard';
|
||||||
|
import { addMetricToDashboardConfig } from './addMetricToDashboard';
|
||||||
|
import { removeMetricFromDashboardConfig } from './removeMetricFromDashboard';
|
||||||
|
|
||||||
|
export const addAndRemoveMetricsToDashboard = (
|
||||||
|
metricIds: string[],
|
||||||
|
existingConfig: BusterDashboard['config']
|
||||||
|
): BusterDashboard['config'] => {
|
||||||
|
// Get all existing metric IDs from the dashboard
|
||||||
|
const existingMetricIds = new Set(
|
||||||
|
existingConfig.rows?.flatMap((row) => row.items.map((item) => item.id)) || []
|
||||||
|
);
|
||||||
|
|
||||||
|
// Determine which metrics to add and remove
|
||||||
|
const metricsToAdd = metricIds.filter((id) => !existingMetricIds.has(id));
|
||||||
|
const metricsToRemove = Array.from(existingMetricIds).filter((id) => !metricIds.includes(id));
|
||||||
|
|
||||||
|
// If no changes needed, return existing config
|
||||||
|
if (metricsToAdd.length === 0 && metricsToRemove.length === 0) {
|
||||||
|
return existingConfig;
|
||||||
|
}
|
||||||
|
|
||||||
|
// First remove metrics if any
|
||||||
|
const configAfterRemoval =
|
||||||
|
metricsToRemove.length > 0
|
||||||
|
? removeMetricFromDashboardConfig(metricsToRemove, existingConfig)
|
||||||
|
: existingConfig;
|
||||||
|
|
||||||
|
// Then add new metrics if any
|
||||||
|
const finalConfig =
|
||||||
|
metricsToAdd.length > 0
|
||||||
|
? addMetricToDashboardConfig(metricsToAdd, configAfterRemoval)
|
||||||
|
: configAfterRemoval;
|
||||||
|
|
||||||
|
return finalConfig;
|
||||||
|
};
|
|
@ -26,6 +26,7 @@ import {
|
||||||
} from '../collections/queryRequests';
|
} from '../collections/queryRequests';
|
||||||
import { collectionQueryKeys } from '@/api/query_keys/collection';
|
import { collectionQueryKeys } from '@/api/query_keys/collection';
|
||||||
import { addMetricToDashboardConfig, removeMetricFromDashboardConfig } from './helpers';
|
import { addMetricToDashboardConfig, removeMetricFromDashboardConfig } from './helpers';
|
||||||
|
import { addAndRemoveMetricsToDashboard } from './helpers/addAndRemoveMetricsToDashboard';
|
||||||
|
|
||||||
export const useGetDashboardsList = (
|
export const useGetDashboardsList = (
|
||||||
params: Omit<DashboardsListRequest, 'page_token' | 'page_size'>
|
params: Omit<DashboardsListRequest, 'page_token' | 'page_size'>
|
||||||
|
@ -129,6 +130,7 @@ export const useUpdateDashboardConfig = () => {
|
||||||
const newConfig = create(previousConfig!, (draft) => {
|
const newConfig = create(previousConfig!, (draft) => {
|
||||||
Object.assign(draft, newDashboard);
|
Object.assign(draft, newDashboard);
|
||||||
});
|
});
|
||||||
|
console.log('update', newConfig);
|
||||||
return mutateAsync({
|
return mutateAsync({
|
||||||
id: newDashboard.id,
|
id: newDashboard.id,
|
||||||
config: newConfig
|
config: newConfig
|
||||||
|
@ -330,29 +332,75 @@ export const useUpdateDashboardShare = () => {
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
const useEnsureDashboardConfig = () => {
|
||||||
* Hook for adding metrics to a dashboard. This function also supports removing metrics via the addMetricToDashboardConfig
|
|
||||||
*/
|
|
||||||
export const useAddMetricsToDashboard = () => {
|
|
||||||
const queryClient = useQueryClient();
|
const queryClient = useQueryClient();
|
||||||
const prefetchDashboard = useGetDashboardAndInitializeMetrics();
|
const prefetchDashboard = useGetDashboardAndInitializeMetrics();
|
||||||
const { openErrorMessage } = useBusterNotifications();
|
const { openErrorMessage } = useBusterNotifications();
|
||||||
|
|
||||||
|
const method = useMemoizedFn(async (dashboardId: string) => {
|
||||||
|
const options = dashboardQueryKeys.dashboardGetDashboard(dashboardId);
|
||||||
|
let dashboardResponse = queryClient.getQueryData(options.queryKey);
|
||||||
|
if (!dashboardResponse) {
|
||||||
|
const res = await prefetchDashboard(dashboardId).catch((e) => {
|
||||||
|
openErrorMessage('Failed to save metrics to dashboard. Dashboard not found');
|
||||||
|
return null;
|
||||||
|
});
|
||||||
|
if (res) {
|
||||||
|
queryClient.setQueryData(options.queryKey, res);
|
||||||
|
dashboardResponse = res;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return dashboardResponse;
|
||||||
|
});
|
||||||
|
|
||||||
|
return method;
|
||||||
|
};
|
||||||
|
|
||||||
|
export const useAddAndRemoveMetricsFromDashboard = () => {
|
||||||
|
const queryClient = useQueryClient();
|
||||||
|
const { openErrorMessage } = useBusterNotifications();
|
||||||
|
const ensureDashboardConfig = useEnsureDashboardConfig();
|
||||||
|
|
||||||
const addMetricToDashboard = useMemoizedFn(
|
const addMetricToDashboard = useMemoizedFn(
|
||||||
async ({ metricIds, dashboardId }: { metricIds: string[]; dashboardId: string }) => {
|
async ({ metricIds, dashboardId }: { metricIds: string[]; dashboardId: string }) => {
|
||||||
const options = dashboardQueryKeys.dashboardGetDashboard(dashboardId);
|
const dashboardResponse = await ensureDashboardConfig(dashboardId);
|
||||||
let dashboardResponse = queryClient.getQueryData(options.queryKey);
|
|
||||||
if (!dashboardResponse) {
|
if (dashboardResponse) {
|
||||||
const res = await prefetchDashboard(dashboardId).catch((e) => {
|
const newConfig = addAndRemoveMetricsToDashboard(
|
||||||
openErrorMessage('Failed to save metrics to dashboard. Dashboard not found');
|
metricIds,
|
||||||
return null;
|
dashboardResponse.dashboard.config
|
||||||
|
);
|
||||||
|
console.log('add/remove', newConfig);
|
||||||
|
return dashboardsUpdateDashboard({
|
||||||
|
id: dashboardId,
|
||||||
|
config: newConfig
|
||||||
});
|
});
|
||||||
if (res) {
|
|
||||||
queryClient.setQueryData(options.queryKey, res);
|
|
||||||
dashboardResponse = res;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
openErrorMessage('Failed to save metrics to dashboard');
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
return useMutation({
|
||||||
|
mutationFn: addMetricToDashboard,
|
||||||
|
onSuccess: (data, variables) => {
|
||||||
|
queryClient.invalidateQueries({
|
||||||
|
queryKey: dashboardQueryKeys.dashboardGetDashboard(variables.dashboardId).queryKey
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
export const useAddMetricsToDashboard = () => {
|
||||||
|
const queryClient = useQueryClient();
|
||||||
|
const { openErrorMessage } = useBusterNotifications();
|
||||||
|
const ensureDashboardConfig = useEnsureDashboardConfig();
|
||||||
|
|
||||||
|
const addMetricToDashboard = useMemoizedFn(
|
||||||
|
async ({ metricIds, dashboardId }: { metricIds: string[]; dashboardId: string }) => {
|
||||||
|
const dashboardResponse = await ensureDashboardConfig(dashboardId);
|
||||||
|
|
||||||
if (dashboardResponse) {
|
if (dashboardResponse) {
|
||||||
const newConfig = addMetricToDashboardConfig(metricIds, dashboardResponse.dashboard.config);
|
const newConfig = addMetricToDashboardConfig(metricIds, dashboardResponse.dashboard.config);
|
||||||
return dashboardsUpdateDashboard({
|
return dashboardsUpdateDashboard({
|
||||||
|
@ -378,7 +426,8 @@ export const useAddMetricsToDashboard = () => {
|
||||||
export const useRemoveMetricsFromDashboard = () => {
|
export const useRemoveMetricsFromDashboard = () => {
|
||||||
const { openConfirmModal, openErrorMessage } = useBusterNotifications();
|
const { openConfirmModal, openErrorMessage } = useBusterNotifications();
|
||||||
const queryClient = useQueryClient();
|
const queryClient = useQueryClient();
|
||||||
const prefetchDashboard = useGetDashboardAndInitializeMetrics();
|
const ensureDashboardConfig = useEnsureDashboardConfig();
|
||||||
|
|
||||||
const removeMetricFromDashboard = useMemoizedFn(
|
const removeMetricFromDashboard = useMemoizedFn(
|
||||||
async ({
|
async ({
|
||||||
metricIds,
|
metricIds,
|
||||||
|
@ -390,18 +439,7 @@ export const useRemoveMetricsFromDashboard = () => {
|
||||||
useConfirmModal?: boolean;
|
useConfirmModal?: boolean;
|
||||||
}) => {
|
}) => {
|
||||||
const method = async () => {
|
const method = async () => {
|
||||||
const options = dashboardQueryKeys.dashboardGetDashboard(dashboardId);
|
const dashboardResponse = await ensureDashboardConfig(dashboardId);
|
||||||
let dashboardResponse = queryClient.getQueryData(options.queryKey);
|
|
||||||
if (!dashboardResponse) {
|
|
||||||
const res = await prefetchDashboard(dashboardId).catch((e) => {
|
|
||||||
openErrorMessage('Failed to remove metrics from dashboard. Dashboard not found');
|
|
||||||
return null;
|
|
||||||
});
|
|
||||||
if (res) {
|
|
||||||
queryClient.setQueryData(options.queryKey, res);
|
|
||||||
dashboardResponse = res;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (dashboardResponse) {
|
if (dashboardResponse) {
|
||||||
const newConfig = removeMetricFromDashboardConfig(
|
const newConfig = removeMetricFromDashboardConfig(
|
||||||
|
|
|
@ -4,7 +4,11 @@ import React, { useLayoutEffect, useMemo, useState } from 'react';
|
||||||
import { InputSelectModal, InputSelectModalProps } from '@/components/ui/modal/InputSelectModal';
|
import { InputSelectModal, InputSelectModalProps } from '@/components/ui/modal/InputSelectModal';
|
||||||
import { formatDate } from '@/lib';
|
import { formatDate } from '@/lib';
|
||||||
import { Button } from '@/components/ui/buttons';
|
import { Button } from '@/components/ui/buttons';
|
||||||
import { useAddMetricsToDashboard, useGetDashboard } from '@/api/buster_rest/dashboards';
|
import {
|
||||||
|
useAddAndRemoveMetricsFromDashboard,
|
||||||
|
useAddMetricsToDashboard,
|
||||||
|
useGetDashboard
|
||||||
|
} from '@/api/buster_rest/dashboards';
|
||||||
|
|
||||||
export const AddToDashboardModal: React.FC<{
|
export const AddToDashboardModal: React.FC<{
|
||||||
open: boolean;
|
open: boolean;
|
||||||
|
@ -13,7 +17,7 @@ export const AddToDashboardModal: React.FC<{
|
||||||
}> = React.memo(({ open, onClose, dashboardId }) => {
|
}> = React.memo(({ open, onClose, dashboardId }) => {
|
||||||
const { data: dashboard, isFetched: isFetchedDashboard } = useGetDashboard(dashboardId);
|
const { data: dashboard, isFetched: isFetchedDashboard } = useGetDashboard(dashboardId);
|
||||||
const { data: metrics, isFetched: isFetchedMetrics } = useGetMetricsList({});
|
const { data: metrics, isFetched: isFetchedMetrics } = useGetMetricsList({});
|
||||||
const { mutateAsync: addMetricsToDashboard } = useAddMetricsToDashboard();
|
const { mutateAsync: addAndRemoveMetricsFromDashboard } = useAddAndRemoveMetricsFromDashboard();
|
||||||
|
|
||||||
const [selectedMetrics, setSelectedMetrics] = useState<string[]>([]);
|
const [selectedMetrics, setSelectedMetrics] = useState<string[]>([]);
|
||||||
|
|
||||||
|
@ -43,7 +47,7 @@ export const AddToDashboardModal: React.FC<{
|
||||||
}, [metrics.length]);
|
}, [metrics.length]);
|
||||||
|
|
||||||
const handleAddAndRemoveMetrics = useMemoizedFn(async () => {
|
const handleAddAndRemoveMetrics = useMemoizedFn(async () => {
|
||||||
await addMetricsToDashboard({
|
await addAndRemoveMetricsFromDashboard({
|
||||||
dashboardId: dashboardId,
|
dashboardId: dashboardId,
|
||||||
metricIds: selectedMetrics
|
metricIds: selectedMetrics
|
||||||
});
|
});
|
||||||
|
@ -102,7 +106,7 @@ export const AddToDashboardModal: React.FC<{
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<InputSelectModal
|
<InputSelectModal
|
||||||
width={650}
|
width={665}
|
||||||
open={open}
|
open={open}
|
||||||
onClose={onClose}
|
onClose={onClose}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
|
|
|
@ -23,7 +23,9 @@ import { v4 as uuidv4 } from 'uuid';
|
||||||
import { useMemoizedFn } from '@/hooks';
|
import { useMemoizedFn } from '@/hooks';
|
||||||
import isEqual from 'lodash/isEqual';
|
import isEqual from 'lodash/isEqual';
|
||||||
import { BusterResizeRows } from './BusterResizeRows';
|
import { BusterResizeRows } from './BusterResizeRows';
|
||||||
|
import omit from 'lodash/omit';
|
||||||
import { NUMBER_OF_COLUMNS, NEW_ROW_ID, MIN_ROW_HEIGHT, TOP_SASH_ID } from './helpers';
|
import { NUMBER_OF_COLUMNS, NEW_ROW_ID, MIN_ROW_HEIGHT, TOP_SASH_ID } from './helpers';
|
||||||
|
import { create } from 'mutative';
|
||||||
|
|
||||||
const measuringConfig = {
|
const measuringConfig = {
|
||||||
droppable: {
|
droppable: {
|
||||||
|
@ -60,6 +62,8 @@ export const BusterResizeableGrid: React.FC<{
|
||||||
const onRowLayoutChangePreflight = useMemoizedFn((newLayout: BusterResizeableGridRow[]) => {
|
const onRowLayoutChangePreflight = useMemoizedFn((newLayout: BusterResizeableGridRow[]) => {
|
||||||
const filteredRows = newRowPreflight(newLayout);
|
const filteredRows = newRowPreflight(newLayout);
|
||||||
|
|
||||||
|
console.log(filteredRows);
|
||||||
|
|
||||||
if (checkRowEquality(filteredRows, rows)) {
|
if (checkRowEquality(filteredRows, rows)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -399,9 +403,7 @@ const newRowPreflight = (newRows: BusterResizeableGridRow[]) => {
|
||||||
columnSizes: newColumnSizes
|
columnSizes: newColumnSizes
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
return {
|
return row;
|
||||||
...row
|
|
||||||
};
|
|
||||||
});
|
});
|
||||||
|
|
||||||
return newRowsCopy;
|
return newRowsCopy;
|
||||||
|
|
|
@ -2,7 +2,7 @@ import React from 'react';
|
||||||
|
|
||||||
export type ResizeableGridDragItem = {
|
export type ResizeableGridDragItem = {
|
||||||
id: string;
|
id: string;
|
||||||
children?: React.ReactNode;
|
children: React.ReactNode;
|
||||||
};
|
};
|
||||||
|
|
||||||
export type BusterResizeableGridRow = {
|
export type BusterResizeableGridRow = {
|
||||||
|
|
|
@ -4,7 +4,12 @@ import React, { useEffect, useMemo, useState } from 'react';
|
||||||
import isEmpty from 'lodash/isEmpty';
|
import isEmpty from 'lodash/isEmpty';
|
||||||
import { BusterResizeableGrid, BusterResizeableGridRow } from '@/components/ui/grid';
|
import { BusterResizeableGrid, BusterResizeableGridRow } from '@/components/ui/grid';
|
||||||
import { useDebounceFn, useMemoizedFn } from '@/hooks';
|
import { useDebounceFn, useMemoizedFn } from '@/hooks';
|
||||||
import { hasRemovedMetrics, hasUnmappedMetrics, normalizeNewMetricsIntoGrid } from './helpers';
|
import {
|
||||||
|
hasRemovedMetrics,
|
||||||
|
hasUnmappedMetrics,
|
||||||
|
normalizeNewMetricsIntoGrid,
|
||||||
|
removeChildrenFromItems
|
||||||
|
} from './helpers';
|
||||||
import { DashboardMetricItem } from './DashboardMetricItem';
|
import { DashboardMetricItem } from './DashboardMetricItem';
|
||||||
import { DashboardContentControllerProvider } from './DashboardContentControllerContext';
|
import { DashboardContentControllerProvider } from './DashboardContentControllerContext';
|
||||||
import type {
|
import type {
|
||||||
|
@ -14,6 +19,7 @@ import type {
|
||||||
} from '@/api/asset_interfaces';
|
} from '@/api/asset_interfaces';
|
||||||
import { DashboardEmptyState } from './DashboardEmptyState';
|
import { DashboardEmptyState } from './DashboardEmptyState';
|
||||||
import { type useUpdateDashboardConfig } from '@/api/buster_rest/dashboards';
|
import { type useUpdateDashboardConfig } from '@/api/buster_rest/dashboards';
|
||||||
|
import omit from 'lodash/omit';
|
||||||
|
|
||||||
const DEFAULT_EMPTY_ROWS: DashboardConfig['rows'] = [];
|
const DEFAULT_EMPTY_ROWS: DashboardConfig['rows'] = [];
|
||||||
const DEFAULT_EMPTY_METRICS: Record<string, BusterMetric> = {};
|
const DEFAULT_EMPTY_METRICS: Record<string, BusterMetric> = {};
|
||||||
|
@ -77,7 +83,9 @@ export const DashboardContentController: React.FC<{
|
||||||
);
|
);
|
||||||
|
|
||||||
const onRowLayoutChange = useMemoizedFn((rows: BusterResizeableGridRow[]) => {
|
const onRowLayoutChange = useMemoizedFn((rows: BusterResizeableGridRow[]) => {
|
||||||
if (dashboard) onUpdateDashboardConfig({ rows, id: dashboard.id });
|
if (dashboard) {
|
||||||
|
onUpdateDashboardConfig({ rows: removeChildrenFromItems(rows), id: dashboard.id });
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
const onDragEnd = useMemoizedFn(() => {
|
const onDragEnd = useMemoizedFn(() => {
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
import { DashboardConfig } from '@/api/asset_interfaces/dashboard';
|
import type { DashboardConfig } from '@/api/asset_interfaces/dashboard';
|
||||||
import { BusterMetric } from '@/api/asset_interfaces/metric';
|
import type { BusterMetric } from '@/api/asset_interfaces/metric';
|
||||||
import { BusterResizeableGridRow } from '@/components/ui/grid/interfaces';
|
import { BusterResizeableGridRow } from '@/components/ui/grid';
|
||||||
|
import omit from 'lodash/omit';
|
||||||
|
|
||||||
export const hasUnmappedMetrics = (
|
export const hasUnmappedMetrics = (
|
||||||
metrics: Record<string, BusterMetric>,
|
metrics: Record<string, BusterMetric>,
|
||||||
|
@ -13,7 +14,7 @@ export const hasUnmappedMetrics = (
|
||||||
|
|
||||||
export const hasRemovedMetrics = (
|
export const hasRemovedMetrics = (
|
||||||
metrics: Record<string, BusterMetric>,
|
metrics: Record<string, BusterMetric>,
|
||||||
configRows: BusterResizeableGridRow[]
|
configRows: DashboardConfig['rows'] = []
|
||||||
) => {
|
) => {
|
||||||
const allGridItemsLength = configRows.flatMap((r) => r.items).length;
|
const allGridItemsLength = configRows.flatMap((r) => r.items).length;
|
||||||
|
|
||||||
|
@ -25,3 +26,10 @@ export const hasRemovedMetrics = (
|
||||||
r.items.some((t) => Object.values(metrics).some((m) => t.id === m.id))
|
r.items.some((t) => Object.values(metrics).some((m) => t.id === m.id))
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const removeChildrenFromItems = (row: BusterResizeableGridRow[]) => {
|
||||||
|
return row.map((r) => ({
|
||||||
|
...r,
|
||||||
|
items: r.items.map((i) => omit(i, 'children'))
|
||||||
|
}));
|
||||||
|
};
|
||||||
|
|
Loading…
Reference in New Issue