feat: preferences framework integrated logs & saved logs views

This commit is contained in:
sawhil 2025-05-14 23:50:00 +05:30
parent 5d52731c77
commit 9a7bec31a7
10 changed files with 254 additions and 145 deletions

View File

@ -240,7 +240,6 @@ function ExplorerOptions({
dataSource: sourcepage,
aggregateOperator: StringOperators.NOOP,
});
console.log('uncaught options in saved views', options);
const getUpdatedExtraData = (
extraData: string | undefined,
@ -339,12 +338,6 @@ function ExplorerOptions({
backwardCompatibleOptions = omit(options, 'version');
}
console.log('uncaught backwardCompatibleOptions', {
backwardCompatibleOptions,
esc: extraData?.selectColumns,
osc: options.selectColumns,
});
if (extraData.selectColumns?.length) {
handleOptionsChange({
...backwardCompatibleOptions,
@ -426,7 +419,6 @@ function ExplorerOptions({
updatePreservedViewInLocalStorage(option);
console.log('uncaught options in saved views before call', options);
updateOrRestoreSelectColumns(
option.key,
viewsData?.data?.data,

View File

@ -1,7 +1,4 @@
import getFromLocalstorage from 'api/browser/localstorage/get';
import setToLocalstorage from 'api/browser/localstorage/set';
import { getAggregateKeys } from 'api/queryBuilder/getAttributeKeys';
import { LOCALSTORAGE } from 'constants/localStorage';
import { LogViewMode } from 'container/LogsTable';
import { useGetAggregateKeys } from 'hooks/queryBuilder/useGetAggregateKeys';
import useDebounce from 'hooks/useDebounce';
@ -11,6 +8,7 @@ import {
AllTraceFilterKeys,
AllTraceFilterKeyValue,
} from 'pages/TracesExplorer/Filter/filterUtils';
import { usePreferenceContext } from 'providers/preferences/context/PreferenceContextProvider';
import { useCallback, useEffect, useMemo, useState } from 'react';
import { useQueries } from 'react-query';
import { ErrorResponse, SuccessResponse } from 'types/api';
@ -35,10 +33,10 @@ import {
import { getOptionsFromKeys } from './utils';
interface UseOptionsMenuProps {
storageKey?: string;
dataSource: DataSource;
aggregateOperator: string;
initialOptions?: InitialOptions;
storageKey: LOCALSTORAGE;
}
interface UseOptionsMenu {
@ -48,22 +46,21 @@ interface UseOptionsMenu {
}
const useOptionsMenu = ({
storageKey,
dataSource,
aggregateOperator,
initialOptions = {},
}: UseOptionsMenuProps): UseOptionsMenu => {
const { notifications } = useNotifications();
const {
preferences,
updateColumns,
updateFormatting,
} = usePreferenceContext();
const [searchText, setSearchText] = useState<string>('');
const [isFocused, setIsFocused] = useState<boolean>(false);
const debouncedSearchText = useDebounce(searchText, 300);
const localStorageOptionsQuery = useMemo(
() => getFromLocalstorage(storageKey),
[storageKey],
);
const initialQueryParams = useMemo(
() => ({
searchText: '',
@ -77,7 +74,6 @@ const useOptionsMenu = ({
const {
query: optionsQuery,
queryData: optionsQueryData,
redirectWithQuery: redirectWithOptionsData,
} = useUrlQueryData<OptionsQuery>(URL_OPTIONS, defaultOptionsQuery);
@ -142,14 +138,12 @@ const useOptionsMenu = ({
})
.filter(Boolean) as BaseAutocompleteData[];
// this is the last point where we can set the default columns and if uptil now also we have an empty array then we will set the default columns
if (!initialSelected || !initialSelected?.length) {
initialSelected = defaultTraceSelectedColumns;
}
}
return initialSelected || [];
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [
isFetchedInitialAttributes,
initialOptions?.selectColumns,
@ -171,7 +165,6 @@ const useOptionsMenu = ({
const searchedAttributeKeys = useMemo(() => {
if (searchedAttributesData?.payload?.attributeKeys?.length) {
if (dataSource === DataSource.LOGS) {
// add timestamp and body to the list of attributes
return [
...defaultLogsSelectedColumns,
...searchedAttributesData.payload.attributeKeys.filter(
@ -188,32 +181,31 @@ const useOptionsMenu = ({
return [];
}, [dataSource, searchedAttributesData?.payload?.attributeKeys]);
const initialOptionsQuery: OptionsQuery = useMemo(
() => ({
const initialOptionsQuery: OptionsQuery = useMemo(() => {
const defaultColumns =
dataSource === DataSource.TRACES
? defaultTraceSelectedColumns
: defaultOptionsQuery.selectColumns;
return {
...defaultOptionsQuery,
...initialOptions,
// eslint-disable-next-line no-nested-ternary
selectColumns: initialOptions?.selectColumns
? initialSelectedColumns
: dataSource === DataSource.TRACES
? defaultTraceSelectedColumns
: defaultOptionsQuery.selectColumns,
}),
[dataSource, initialOptions, initialSelectedColumns],
);
: defaultColumns,
};
}, [dataSource, initialOptions, initialSelectedColumns]);
const selectedColumnKeys = useMemo(
() => optionsQueryData?.selectColumns?.map(({ id }) => id) || [],
[optionsQueryData],
() => preferences?.columns?.map(({ id }) => id) || [],
[preferences?.columns],
);
const optionsFromAttributeKeys = useMemo(() => {
const filteredAttributeKeys = searchedAttributeKeys.filter((item) => {
// For other data sources, only filter out 'body' if it exists
if (dataSource !== DataSource.LOGS) {
return item.key !== 'body';
}
// For LOGS, keep all keys
return true;
});
@ -223,10 +215,8 @@ const useOptionsMenu = ({
const handleRedirectWithOptionsData = useCallback(
(newQueryData: OptionsQuery) => {
redirectWithOptionsData(newQueryData);
setToLocalstorage(storageKey, JSON.stringify(newQueryData));
},
[storageKey, redirectWithOptionsData],
[redirectWithOptionsData],
);
const handleSelectColumns = useCallback(
@ -235,7 +225,7 @@ const useOptionsMenu = ({
const newSelectedColumns = newSelectedColumnKeys.reduce((acc, key) => {
const column = [
...searchedAttributeKeys,
...optionsQueryData.selectColumns,
...(preferences?.columns || []),
].find(({ id }) => id === key);
if (!column) return acc;
@ -243,75 +233,122 @@ const useOptionsMenu = ({
}, [] as BaseAutocompleteData[]);
const optionsData: OptionsQuery = {
...optionsQueryData,
...defaultOptionsQuery,
selectColumns: newSelectedColumns,
format: preferences?.formatting?.format || defaultOptionsQuery.format,
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
};
updateColumns(newSelectedColumns);
handleRedirectWithOptionsData(optionsData);
},
[
searchedAttributeKeys,
selectedColumnKeys,
optionsQueryData,
preferences,
handleRedirectWithOptionsData,
updateColumns,
],
);
const handleRemoveSelectedColumn = useCallback(
(columnKey: string) => {
const newSelectedColumns = optionsQueryData?.selectColumns?.filter(
const newSelectedColumns = preferences?.columns?.filter(
({ id }) => id !== columnKey,
);
if (!newSelectedColumns.length && dataSource !== DataSource.LOGS) {
if (!newSelectedColumns?.length && dataSource !== DataSource.LOGS) {
notifications.error({
message: 'There must be at least one selected column',
});
} else {
const optionsData: OptionsQuery = {
...optionsQueryData,
selectColumns: newSelectedColumns,
...defaultOptionsQuery,
selectColumns: newSelectedColumns || [],
format: preferences?.formatting?.format || defaultOptionsQuery.format,
maxLines:
preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
fontSize:
preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
};
updateColumns(newSelectedColumns || []);
handleRedirectWithOptionsData(optionsData);
}
},
[dataSource, notifications, optionsQueryData, handleRedirectWithOptionsData],
[
dataSource,
notifications,
preferences,
handleRedirectWithOptionsData,
updateColumns,
],
);
const handleFormatChange = useCallback(
(value: LogViewMode) => {
const optionsData: OptionsQuery = {
...optionsQueryData,
...defaultOptionsQuery,
selectColumns: preferences?.columns || [],
format: value,
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
};
updateFormatting({
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
format: value === 'list' ? 'table' : value,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
});
handleRedirectWithOptionsData(optionsData);
},
[handleRedirectWithOptionsData, optionsQueryData],
[handleRedirectWithOptionsData, preferences, updateFormatting],
);
const handleMaxLinesChange = useCallback(
(value: string | number | null) => {
const optionsData: OptionsQuery = {
...optionsQueryData,
...defaultOptionsQuery,
selectColumns: preferences?.columns || [],
format: preferences?.formatting?.format || defaultOptionsQuery.format,
maxLines: value as number,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
};
updateFormatting({
maxLines: value as number,
format:
preferences?.formatting?.format === 'list'
? 'table'
: preferences?.formatting?.format || defaultOptionsQuery.format,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
});
handleRedirectWithOptionsData(optionsData);
},
[handleRedirectWithOptionsData, optionsQueryData],
[handleRedirectWithOptionsData, preferences, updateFormatting],
);
const handleFontSizeChange = useCallback(
(value: FontSize) => {
const optionsData: OptionsQuery = {
...optionsQueryData,
...defaultOptionsQuery,
selectColumns: preferences?.columns || [],
format: preferences?.formatting?.format || defaultOptionsQuery.format,
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
fontSize: value,
};
updateFormatting({
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
format:
preferences?.formatting?.format === 'list'
? 'table'
: preferences?.formatting?.format || defaultOptionsQuery.format,
fontSize: value,
});
handleRedirectWithOptionsData(optionsData);
},
[handleRedirectWithOptionsData, optionsQueryData],
[handleRedirectWithOptionsData, preferences, updateFormatting],
);
const handleSearchAttribute = useCallback((value: string) => {
@ -331,7 +368,7 @@ const useOptionsMenu = ({
() => ({
addColumn: {
isFetching: isSearchedAttributesFetching,
value: optionsQueryData?.selectColumns || defaultOptionsQuery.selectColumns,
value: preferences?.columns || defaultOptionsQuery.selectColumns,
options: optionsFromAttributeKeys || [],
onFocus: handleFocus,
onBlur: handleBlur,
@ -340,24 +377,21 @@ const useOptionsMenu = ({
onSearch: handleSearchAttribute,
},
format: {
value: optionsQueryData.format || defaultOptionsQuery.format,
value: preferences?.formatting?.format || defaultOptionsQuery.format,
onChange: handleFormatChange,
},
maxLines: {
value: optionsQueryData.maxLines || defaultOptionsQuery.maxLines,
value: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
onChange: handleMaxLinesChange,
},
fontSize: {
value: optionsQueryData?.fontSize || defaultOptionsQuery.fontSize,
value: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
onChange: handleFontSizeChange,
},
}),
[
isSearchedAttributesFetching,
optionsQueryData?.selectColumns,
optionsQueryData.format,
optionsQueryData.maxLines,
optionsQueryData?.fontSize,
preferences,
optionsFromAttributeKeys,
handleSelectColumns,
handleRemoveSelectedColumn,
@ -371,21 +405,21 @@ const useOptionsMenu = ({
useEffect(() => {
if (optionsQuery || !isFetchedInitialAttributes) return;
const nextOptionsQuery = localStorageOptionsQuery
? JSON.parse(localStorageOptionsQuery)
: initialOptionsQuery;
redirectWithOptionsData(nextOptionsQuery);
redirectWithOptionsData(initialOptionsQuery);
}, [
isFetchedInitialAttributes,
optionsQuery,
initialOptionsQuery,
localStorageOptionsQuery,
redirectWithOptionsData,
]);
return {
options: optionsQueryData,
options: {
selectColumns: preferences?.columns || [],
format: preferences?.formatting?.format || defaultOptionsQuery.format,
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
},
config: optionsMenuConfig,
handleOptionsChange: handleRedirectWithOptionsData,
};

View File

@ -36,9 +36,8 @@ function LogsExplorer(): JSX.Element {
const [selectedView, setSelectedView] = useState<SELECTED_VIEWS>(
SELECTED_VIEWS.SEARCH,
);
const { preferences, updateFormatting } = usePreferenceContext();
const { preferences } = usePreferenceContext();
console.log('uncaught preferences', preferences);
const [showFilters, setShowFilters] = useState<boolean>(() => {
const localStorageValue = getLocalStorageKey(
LOCALSTORAGE.SHOW_LOGS_QUICK_FILTERS,
@ -87,7 +86,6 @@ function LogsExplorer(): JSX.Element {
}, [currentQuery.builder.queryData, currentQuery.builder.queryData.length]);
const {
queryData: optionsQueryData,
redirectWithQuery: redirectWithOptionsData,
} = useUrlQueryData<OptionsQuery>(URL_OPTIONS, defaultOptionsQuery);
@ -168,12 +166,32 @@ function LogsExplorer(): JSX.Element {
);
useEffect(() => {
const migratedQuery = migrateOptionsQuery(optionsQueryData);
const migratedQuery = migrateOptionsQuery(
preferences
? {
selectColumns: preferences.columns || [],
maxLines:
preferences.formatting?.maxLines || defaultOptionsQuery.maxLines,
format: preferences.formatting?.format || defaultOptionsQuery.format,
fontSize:
preferences.formatting?.fontSize || defaultOptionsQuery.fontSize,
version: preferences.formatting?.version,
}
: defaultOptionsQuery,
);
// Only redirect if the query was actually modified
if (!isEqual(migratedQuery, optionsQueryData)) {
if (
!isEqual(migratedQuery, {
selectColumns: preferences?.columns || [],
maxLines: preferences?.formatting?.maxLines || defaultOptionsQuery.maxLines,
format: preferences?.formatting?.format || defaultOptionsQuery.format,
fontSize: preferences?.formatting?.fontSize || defaultOptionsQuery.fontSize,
version: preferences?.formatting?.version,
})
) {
redirectWithOptionsData(migratedQuery);
}
}, [migrateOptionsQuery, optionsQueryData, redirectWithOptionsData]);
}, [migrateOptionsQuery, preferences, redirectWithOptionsData]);
const isMultipleQueries = useMemo(
() =>
@ -226,21 +244,6 @@ function LogsExplorer(): JSX.Element {
</section>
)}
<section className={cx('log-module-right-section')}>
{/* dummy button to test the updateFormatting function */}
<div>
<button
type="button"
onClick={(): void => updateFormatting({ maxLines: 10 })}
>
<h1>Update formatting</h1>
</button>
</div>
{preferences && (
<div>
<h1>Preferences</h1>
<pre>{JSON.stringify(preferences, null, 2)}</pre>
</div>
)}
<Toolbar
showAutoRefresh={false}
leftActions={

View File

@ -2,6 +2,7 @@
import getLocalStorageKey from 'api/browser/localstorage/get';
import { LOCALSTORAGE } from 'constants/localStorage';
import { defaultLogsSelectedColumns } from 'container/OptionsMenu/constants';
import { FontSize } from 'container/OptionsMenu/types';
import { BaseAutocompleteData } from 'types/api/queryBuilder/queryAutocompleteResponse';
import { FormattingOptions } from '../types';
@ -56,7 +57,7 @@ const logsLoaders = {
formatting: {
maxLines: 2,
format: 'table',
fontSize: 'small',
fontSize: 'small' as FontSize,
version: 1,
},
}),

View File

@ -1,20 +1,39 @@
import setLocalStorageKey from 'api/browser/localstorage/set';
import { LOCALSTORAGE } from 'constants/localStorage';
import { defaultOptionsQuery } from 'container/OptionsMenu/constants';
import { FontSize, OptionsQuery } from 'container/OptionsMenu/types';
import { Dispatch, SetStateAction } from 'react';
import { BaseAutocompleteData } from 'types/api/queryBuilder/queryAutocompleteResponse';
import { FormattingOptions } from '../types';
import { FormattingOptions, Preferences } from '../types';
// --- LOGS preferences updater config ---
const logsUpdater = {
const getLogsUpdaterConfig = (
redirectWithOptionsData: (options: OptionsQuery) => void,
setSavedViewPreferences: Dispatch<SetStateAction<Preferences | null>>,
): {
updateColumns: (newColumns: BaseAutocompleteData[], mode: string) => void;
updateFormatting: (newFormatting: FormattingOptions, mode: string) => void;
} => ({
updateColumns: (newColumns: BaseAutocompleteData[], mode: string): void => {
// Always update URL
const url = new URL(window.location.href);
const options = JSON.parse(url.searchParams.get('options') || '{}');
options.selectColumns = newColumns;
url.searchParams.set('options', JSON.stringify(options));
window.history.replaceState({}, '', url.toString());
if (mode === 'savedView') {
setSavedViewPreferences({
columns: newColumns,
formatting: {
maxLines: 2,
format: 'table',
fontSize: 'small' as FontSize,
version: 1,
},
});
}
if (mode === 'direct') {
// redirectWithOptionsData({
// ...defaultOptionsQuery,
// selectColumns: newColumns,
// });
// Also update local storage
const local = JSON.parse(
localStorage.getItem(LOCALSTORAGE.LOGS_LIST_OPTIONS) || '{}',
@ -25,11 +44,10 @@ const logsUpdater = {
},
updateFormatting: (newFormatting: FormattingOptions, mode: string): void => {
// Always update URL
const url = new URL(window.location.href);
const options = JSON.parse(url.searchParams.get('options') || '{}');
Object.assign(options, newFormatting);
url.searchParams.set('options', JSON.stringify(options));
window.history.replaceState({}, '', url.toString());
redirectWithOptionsData({
...defaultOptionsQuery,
...newFormatting,
});
if (mode === 'direct') {
// Also update local storage
@ -40,6 +58,6 @@ const logsUpdater = {
setLocalStorageKey(LOCALSTORAGE.LOGS_LIST_OPTIONS, JSON.stringify(local));
}
},
};
});
export default logsUpdater;
export default getLogsUpdaterConfig;

View File

@ -23,7 +23,15 @@ export function PreferenceContextProvider({
const location = useLocation();
const params = new URLSearchParams(location.search);
const savedViewId = params.get('view');
let savedViewId = '';
const viewKeyParam = params.get('viewKey');
if (viewKeyParam) {
try {
savedViewId = JSON.parse(viewKeyParam);
} catch (e) {
console.error(e);
}
}
let dataSource: DataSource = DataSource.LOGS;
if (location.pathname.includes('traces')) dataSource = DataSource.TRACES;

View File

@ -1,12 +1,11 @@
/* eslint-disable sonarjs/cognitive-complexity */
/* eslint-disable no-empty */
import {
defaultLogsSelectedColumns,
defaultTraceSelectedColumns,
} from 'container/OptionsMenu/constants';
// import {
// defaultLogsSelectedColumns,
// defaultTraceSelectedColumns,
// } from 'container/OptionsMenu/constants';
import { useGetAllViews } from 'hooks/saveViews/useGetAllViews';
import { useEffect, useState } from 'react';
import { useLocation } from 'react-router-dom';
import { BaseAutocompleteData } from 'types/api/queryBuilder/queryAutocompleteResponse';
import { DataSource } from 'types/common/queryBuilder';
@ -71,12 +70,9 @@ export function usePreferenceLoader({
const [preferences, setPreferences] = useState<Preferences | null>(null);
const [loading, setLoading] = useState(true);
const [error, setError] = useState<Error | null>(null);
const location = useLocation();
const { data: viewsData } = useGetAllViews(dataSource);
console.log('uncaught viewsData', viewsData);
useEffect((): void => {
async function loadPreferences(): Promise<void> {
setLoading(true);
@ -87,25 +83,24 @@ export function usePreferenceLoader({
// we can also switch to the URL options params
// as we are essentially setting the options in the URL
// in ExplorerOptions.tsx#430 (updateOrRestoreSelectColumns)
const extraData = viewsData?.data?.data?.find(
(view) => view.id === savedViewId,
)?.extraData;
const parsedExtraData = JSON.parse(extraData || '{}');
let columns: BaseAutocompleteData[] = [];
let formatting: FormattingOptions | undefined;
if (dataSource === DataSource.LOGS) {
columns = parsedExtraData?.selectColumns || defaultLogsSelectedColumns;
formatting = {
maxLines: parsedExtraData?.maxLines ?? 2,
format: parsedExtraData?.format ?? 'table',
fontSize: parsedExtraData?.fontSize ?? 'small',
version: parsedExtraData?.version ?? 1,
};
} else if (dataSource === DataSource.TRACES) {
columns = parsedExtraData?.selectColumns || defaultTraceSelectedColumns;
}
setPreferences({ columns, formatting });
// const extraData = viewsData?.data?.data?.find(
// (view) => view.id === savedViewId,
// )?.extraData;
// const parsedExtraData = JSON.parse(extraData || '{}');
// let columns: BaseAutocompleteData[] = [];
// let formatting: FormattingOptions | undefined;
// if (dataSource === DataSource.LOGS) {
// columns = parsedExtraData?.selectColumns || defaultLogsSelectedColumns;
// formatting = {
// maxLines: parsedExtraData?.maxLines ?? 2,
// format: parsedExtraData?.format ?? 'table',
// fontSize: parsedExtraData?.fontSize ?? 'small',
// version: parsedExtraData?.version ?? 1,
// };
// } else if (dataSource === DataSource.TRACES) {
// columns = parsedExtraData?.selectColumns || defaultTraceSelectedColumns;
// }
// setPreferences(savedViewPreferences);
} else {
if (dataSource === DataSource.LOGS) {
const { columns, formatting } = await logsPreferencesLoader();
@ -124,7 +119,7 @@ export function usePreferenceLoader({
}
}
loadPreferences();
}, [mode, savedViewId, dataSource, location, reSync, viewsData]);
}, [mode, savedViewId, dataSource, reSync, viewsData]);
return { preferences, loading, error };
}

View File

@ -1,4 +1,6 @@
import { useState } from 'react';
import { defaultLogsSelectedColumns } from 'container/OptionsMenu/constants';
import { useGetAllViews } from 'hooks/saveViews/useGetAllViews';
import { useEffect, useState } from 'react';
import { BaseAutocompleteData } from 'types/api/queryBuilder/queryAutocompleteResponse';
import { DataSource } from 'types/common/queryBuilder';
@ -21,6 +23,32 @@ export function usePreferenceSync({
updateColumns: (newColumns: BaseAutocompleteData[]) => void;
updateFormatting: (newFormatting: FormattingOptions) => void;
} {
const { data: viewsData } = useGetAllViews(dataSource);
const [
savedViewPreferences,
setSavedViewPreferences,
] = useState<Preferences | null>(null);
useEffect(() => {
const extraData = viewsData?.data?.data?.find(
(view) => view.id === savedViewId,
)?.extraData;
const parsedExtraData = JSON.parse(extraData || '{}');
let columns: BaseAutocompleteData[] = [];
let formatting: FormattingOptions | undefined;
if (dataSource === DataSource.LOGS) {
columns = parsedExtraData?.selectColumns || defaultLogsSelectedColumns;
formatting = {
maxLines: parsedExtraData?.maxLines ?? 2,
format: parsedExtraData?.format ?? 'table',
fontSize: parsedExtraData?.fontSize ?? 'small',
version: parsedExtraData?.version ?? 1,
};
}
setSavedViewPreferences({ columns, formatting });
}, [viewsData, dataSource, savedViewId, mode]);
// We are using a reSync state because we have URL updates as well as local storage updates
// and we want to make sure we are always using the latest preferences
const [reSync, setReSync] = useState(0);
@ -35,7 +63,15 @@ export function usePreferenceSync({
dataSource,
mode,
setReSync,
setSavedViewPreferences,
});
return { preferences, loading, error, updateColumns, updateFormatting };
return {
preferences:
mode === 'savedView' && savedViewId ? savedViewPreferences : preferences,
loading,
error,
updateColumns,
updateFormatting,
};
}

View File

@ -1,3 +1,5 @@
import { LogViewMode } from 'container/LogsTable';
import { FontSize } from 'container/OptionsMenu/types';
import { BaseAutocompleteData } from 'types/api/queryBuilder/queryAutocompleteResponse';
import { DataSource } from 'types/common/queryBuilder';
@ -16,8 +18,8 @@ export interface PreferenceContextValue {
export interface FormattingOptions {
maxLines?: number;
format?: 'raw' | 'table';
fontSize?: 'small' | 'medium' | 'large';
format?: LogViewMode;
fontSize?: FontSize;
version?: number;
}

View File

@ -1,41 +1,61 @@
import {
defaultOptionsQuery,
URL_OPTIONS,
} from 'container/OptionsMenu/constants';
import { OptionsQuery } from 'container/OptionsMenu/types';
import useUrlQueryData from 'hooks/useUrlQueryData';
import { Dispatch, SetStateAction } from 'react';
import { BaseAutocompleteData } from 'types/api/queryBuilder/queryAutocompleteResponse';
import { DataSource } from 'types/common/queryBuilder';
import logsUpdater from '../configs/logsUpdaterConfig';
import getLogsUpdaterConfig from '../configs/logsUpdaterConfig';
import tracesUpdater from '../configs/tracesUpdaterConfig';
import { FormattingOptions } from '../types';
import { FormattingOptions, Preferences } from '../types';
const metricsUpdater = {
updateColumns: (): void => {}, // no-op for metrics
updateFormatting: (): void => {}, // no-op for metrics
};
const updaterConfig: Record<
const getUpdaterConfig = (
redirectWithOptionsData: (options: OptionsQuery) => void,
setSavedViewPreferences: Dispatch<SetStateAction<Preferences | null>>,
): Record<
DataSource,
{
updateColumns: (newColumns: BaseAutocompleteData[], mode: string) => void;
updateFormatting: (newFormatting: FormattingOptions, mode: string) => void;
}
> = {
[DataSource.LOGS]: logsUpdater,
> => ({
[DataSource.LOGS]: getLogsUpdaterConfig(
redirectWithOptionsData,
setSavedViewPreferences,
),
[DataSource.TRACES]: tracesUpdater,
[DataSource.METRICS]: metricsUpdater,
};
});
export function usePreferenceUpdater({
dataSource,
mode,
setReSync,
setSavedViewPreferences,
}: {
dataSource: DataSource;
mode: string;
setReSync: Dispatch<SetStateAction<number>>;
setSavedViewPreferences: Dispatch<SetStateAction<Preferences | null>>;
}): {
updateColumns: (newColumns: BaseAutocompleteData[]) => void;
updateFormatting: (newFormatting: FormattingOptions) => void;
} {
const updater = updaterConfig[dataSource];
const {
redirectWithQuery: redirectWithOptionsData,
} = useUrlQueryData<OptionsQuery>(URL_OPTIONS, defaultOptionsQuery);
const updater = getUpdaterConfig(
redirectWithOptionsData,
setSavedViewPreferences,
)[dataSource];
return {
updateColumns: (newColumns: BaseAutocompleteData[]): void => {