From 4fa3439399936ad7432e46773ae56d81c39ba204 Mon Sep 17 00:00:00 2001 From: Koustav Das <78158736+Koustavd18@users.noreply.github.com> Date: Thu, 19 Dec 2024 14:26:05 +0530 Subject: [PATCH] Fix: URL params (#371) --- playwright.config.ts | 4 + src/hooks/useQueryLogs.ts | 6 +- src/pages/Stream/Views/Explore/Footer.tsx | 48 +++++----- src/pages/Stream/Views/Explore/LogsView.tsx | 38 +++++++- .../Stream/Views/Explore/useLogsFetcher.ts | 2 +- src/pages/Stream/components/Querier/index.tsx | 4 +- src/pages/Stream/hooks/useParamsController.ts | 96 ++++++++++++++----- src/pages/Stream/providers/FilterProvider.tsx | 29 ++++++ src/pages/Stream/providers/LogsProvider.tsx | 26 +++++ src/utils/index.ts | 18 ++++ 10 files changed, 218 insertions(+), 53 deletions(-) diff --git a/playwright.config.ts b/playwright.config.ts index 5c90d80b..cbcc6b5a 100644 --- a/playwright.config.ts +++ b/playwright.config.ts @@ -21,6 +21,10 @@ export default defineConfig({ /* Collect trace when retrying the failed test. See https://playwright.dev/docs/trace-viewer */ trace: 'on-first-retry', }, + timeout: 20000, // Timeout for each test + expect: { + timeout: 20000, // Timeout for `expect` assertions + }, /* Configure projects for major browsers */ projects: [ diff --git a/src/hooks/useQueryLogs.ts b/src/hooks/useQueryLogs.ts index 62ab8997..af683d04 100644 --- a/src/hooks/useQueryLogs.ts +++ b/src/hooks/useQueryLogs.ts @@ -57,6 +57,7 @@ export const useQueryLogs = () => { setLogsStore, ] = useLogsStore((store) => store); const [appliedQuery] = useFilterStore((store) => store.appliedQuery); + const [isQueryFromParams] = useFilterStore((store) => store.isQueryFromParams); const { isQuerySearchActive, custSearchQuery, activeMode } = custQuerySearchState; const getColumnFilters = useCallback( @@ -99,7 +100,7 @@ export const useQueryLogs = () => { () => { refetchSchema(); if (isQuerySearchActive) { - if (activeMode === 'filters') { + if (activeMode === 'filters' && isQueryFromParams === false) { const { parsedQuery } = parseQuery(queryEngine, appliedQuery, currentStream || '', { startTime: timeRange.startTime, endTime: timeRange.endTime, @@ -107,6 +108,9 @@ export const useQueryLogs = () => { }); const queryStrWithOffset = appendOffsetToQuery(parsedQuery, defaultQueryOpts.pageOffset); return getQueryResultWithHeaders({ ...defaultQueryOpts, access: [] }, queryStrWithOffset); + } else if (activeMode === 'filters' && isQueryFromParams === true) { + const queryStrWithOffset = appendOffsetToQuery(custSearchQuery, defaultQueryOpts.pageOffset); + return getQueryResultWithHeaders({ ...defaultQueryOpts, access: [] }, queryStrWithOffset); } else { const queryStrWithOffset = appendOffsetToQuery(custSearchQuery, defaultQueryOpts.pageOffset); return getQueryResultWithHeaders({ ...defaultQueryOpts, access: [] }, queryStrWithOffset); diff --git a/src/pages/Stream/Views/Explore/Footer.tsx b/src/pages/Stream/Views/Explore/Footer.tsx index 536793ff..ca1f35e2 100644 --- a/src/pages/Stream/Views/Explore/Footer.tsx +++ b/src/pages/Stream/Views/Explore/Footer.tsx @@ -1,4 +1,4 @@ -import { FC, useCallback } from 'react'; +import { FC, useCallback, useEffect } from 'react'; import { useLogsStore, logsStoreReducers, LOAD_LIMIT, LOG_QUERY_LIMITS } from '../../providers/LogsProvider'; import { usePagination } from '@mantine/hooks'; import { Box, Center, Group, Loader, Menu, Pagination, Stack, Tooltip } from '@mantine/core'; @@ -90,14 +90,29 @@ const LimitControl: FC = () => { const Footer = (props: { loaded: boolean; hasNoData: boolean; isFetchingCount: boolean }) => { const [tableOpts, setLogsStore] = useLogsStore((store) => store.tableOpts); - const { totalPages, currentOffset, currentPage, perPage, totalCount } = tableOpts; + const { totalPages, currentOffset, currentPage, perPage, totalCount, targetPage } = tableOpts; - const onPageChange = useCallback((page: number) => { - setLogsStore((store) => setRowNumber(store, '')); - setLogsStore((store) => setPageAndPageData(store, page)); - }, []); + const onPageChange = useCallback( + (page: number) => { + setLogsStore((store) => setPageAndPageData(store, page)); + if (props.loaded && !targetPage) { + setLogsStore((store) => setRowNumber(store, '')); + } + }, + [props.loaded, targetPage], + ); + + useEffect(() => { + if (!props.loaded) return; + pagination.setPage(targetPage ? targetPage : 1); + }, [props.loaded]); + + const pagination = usePagination({ + total: totalPages ?? 1, + initialPage: 1, + onChange: onPageChange, + }); - const pagination = usePagination({ total: totalPages ?? 1, initialPage: 1, onChange: onPageChange }); const onChangeOffset = useCallback( (key: 'prev' | 'next') => { if (key === 'prev') { @@ -132,7 +147,7 @@ const Footer = (props: { loaded: boolean; hasNoData: boolean; isFetchingCount: b total={totalPages} value={currentPage} onChange={(page) => { - pagination.setPage(page); + pagination && pagination.setPage(page); }} size="sm"> @@ -172,23 +187,6 @@ const Footer = (props: { loaded: boolean; hasNoData: boolean; isFetchingCount: b ) : null} - {/* {props.loaded && ( - - -
- -
-
- - exportHandler('CSV')} style={{ padding: '0.5rem 2.25rem 0.5rem 0.75rem' }}> - CSV - - exportHandler('JSON')} style={{ padding: '0.5rem 2.25rem 0.5rem 0.75rem' }}> - JSON - - -
- )} */}
diff --git a/src/pages/Stream/Views/Explore/LogsView.tsx b/src/pages/Stream/Views/Explore/LogsView.tsx index 4dbf0d11..92601a78 100644 --- a/src/pages/Stream/Views/Explore/LogsView.tsx +++ b/src/pages/Stream/Views/Explore/LogsView.tsx @@ -1,18 +1,28 @@ import { Box } from '@mantine/core'; -import { useLogsStore } from '../../providers/LogsProvider'; +import { useLogsStore, logsStoreReducers } from '../../providers/LogsProvider'; import JsonView from './JSONView'; import LogTable from './StaticLogTable'; import useLogsFetcher from './useLogsFetcher'; import LogsViewConfig from './LogsViewConfig'; +import { useFilterStore, filterStoreReducers } from '../../providers/FilterProvider'; + +import { useEffect } from 'react'; +import _ from 'lodash'; + +const { setPageAndPageData, setTargetPage, setTargetColumns, setDisabledColumns } = logsStoreReducers; +const { toogleQueryParamsFlag } = filterStoreReducers; const LogsView = (props: { schemaLoading: boolean; infoLoading: boolean }) => { + const [, setFilterStore] = useFilterStore((store) => store); const { schemaLoading, infoLoading } = props; const { errorMessage, hasNoData, showTable, isFetchingCount, logsLoading } = useLogsFetcher({ schemaLoading, infoLoading, }); - const [viewMode] = useLogsStore((store) => store.viewMode); + const [tableOpts] = useLogsStore((store) => store.tableOpts); + const { currentPage, targetPage, headers, targetColumns } = tableOpts; + const [viewMode, setLogsStore] = useLogsStore((store) => store.viewMode); const viewOpts = { errorMessage, hasNoData, @@ -21,6 +31,30 @@ const LogsView = (props: { schemaLoading: boolean; infoLoading: boolean }) => { logsLoading, }; + useEffect(() => { + if (!showTable) return; + if (targetPage) { + setLogsStore((store) => setPageAndPageData(store, targetPage)); + if (currentPage === targetPage) { + setLogsStore((store) => setTargetPage(store, undefined)); + } + } + if (showTable) setFilterStore((store) => toogleQueryParamsFlag(store, false)); + }, [showTable, currentPage]); + + useEffect(() => { + if (!showTable) return; + if (!_.isEmpty(targetColumns)) { + setLogsStore((store) => + setDisabledColumns( + store, + headers.filter((el) => !targetColumns.includes(el)), + ), + ); + setLogsStore((store) => setTargetColumns(store, [])); + } + }, [headers]); + return ( {viewMode === 'table' && ( diff --git a/src/pages/Stream/Views/Explore/useLogsFetcher.ts b/src/pages/Stream/Views/Explore/useLogsFetcher.ts index 96a6435e..2d76ef57 100644 --- a/src/pages/Stream/Views/Explore/useLogsFetcher.ts +++ b/src/pages/Stream/Views/Explore/useLogsFetcher.ts @@ -31,7 +31,7 @@ const useLogsFetcher = (props: { schemaLoading: boolean; infoLoading: boolean }) useEffect(() => { if (infoLoading || !firstEventAt) return; - if (currentPage === 0 && currentOffset === 0) { + if (currentPage === 0) { getQueryData(); refetchCount(); } diff --git a/src/pages/Stream/components/Querier/index.tsx b/src/pages/Stream/components/Querier/index.tsx index 4ca6dbb8..8559f13d 100644 --- a/src/pages/Stream/components/Querier/index.tsx +++ b/src/pages/Stream/components/Querier/index.tsx @@ -133,7 +133,7 @@ const Querier = () => { }, []); const [schema] = useStreamStore((store) => store.schema); const [streamInfo] = useStreamStore((store) => store.info); - const [{ query, isSumbitDisabled }, setFilterStore] = useFilterStore((store) => store); + const [{ query, isSumbitDisabled, isQueryFromParams }, setFilterStore] = useFilterStore((store) => store); const timePartitionColumn = _.get(streamInfo, 'time_partition', 'p_timestamp'); useEffect(() => { @@ -202,7 +202,7 @@ const Querier = () => { // trigger query fetch if the rules were updated by the remove btn on pills // ----------------------------------- - if (!showQueryBuilder && (activeMode === 'filters' || savedFilterId)) { + if (!showQueryBuilder && (activeMode === 'filters' || savedFilterId) && !isQueryFromParams) { if (!shouldSumbitDisabled) { onFiltersApply({ isUncontrolled: true }); } else { diff --git a/src/pages/Stream/hooks/useParamsController.ts b/src/pages/Stream/hooks/useParamsController.ts index c048edbd..12efc497 100644 --- a/src/pages/Stream/hooks/useParamsController.ts +++ b/src/pages/Stream/hooks/useParamsController.ts @@ -3,20 +3,32 @@ import { useLogsStore, logsStoreReducers } from '@/pages/Stream/providers/LogsPr import { useSearchParams } from 'react-router-dom'; import _ from 'lodash'; import { FIXED_DURATIONS } from '@/constants/timeConstants'; -import { LOG_QUERY_LIMITS } from '@/pages/Stream/providers/LogsProvider'; +import { LOG_QUERY_LIMITS, columnsToSkip } from '@/pages/Stream/providers/LogsProvider'; import dayjs from 'dayjs'; import timeRangeUtils from '@/utils/timeRangeUtils'; import moment from 'moment-timezone'; import { filterStoreReducers, QueryType, useFilterStore } from '../providers/FilterProvider'; import { generateQueryBuilderASTFromSQL } from '../utils'; import { appStoreReducers, TimeRange, useAppStore } from '@/layouts/MainLayout/providers/AppProvider'; +import { getOffset, joinOrSplit } from '@/utils'; const { getRelativeStartAndEndDate, formatDateWithTimezone, getLocalTimezone } = timeRangeUtils; -const { onToggleView, setPerPage, setCustQuerySearchState, setRowNumber } = logsStoreReducers; + const { setTimeRange, syncTimeRange } = appStoreReducers; -const { applySavedFilters } = filterStoreReducers; +const { + onToggleView, + setPerPage, + setCustQuerySearchState, + setTargetPage, + setCurrentOffset, + setTargetColumns, + setRowNumber, +} = logsStoreReducers; +const { toogleQueryParamsFlag, setAppliedFilterQuery, applySavedFilters, updateQuery, updateAppliedQuery } = + filterStoreReducers; + const timeRangeFormat = 'DD-MMM-YYYY_HH-mmz'; -const keys = ['view', 'rows', 'interval', 'from', 'to', 'query', 'filterType', 'rowNumber']; +const keys = ['view', 'rows', 'page', 'interval', 'from', 'to', 'query', 'filterType', 'fields', 'rowNumber']; const dateToParamString = (date: Date) => { return formatDateWithTimezone(date, timeRangeFormat); @@ -63,23 +75,24 @@ const deriveRowNumber = (rowNumber: string) => { const storeToParamsObj = (opts: { timeRange: TimeRange; view: string; - offset: string; page: string; rows: string; query: string; filterType: string; + fields: string; rowNumber: string; }): Record => { - const { timeRange, offset, page, view, rows, query, filterType, rowNumber } = opts; + const { timeRange, page, view, rows, query, filterType, fields, rowNumber } = opts; + const params: Record = { ...deriveTimeRangeParams(timeRange), ...deriveRowNumber(rowNumber), view, - offset, rows, page, query, filterType: query ? filterType : '', + fields, }; return _.pickBy(params, (val, key) => !_.isEmpty(val) && _.includes(keys, key)); }; @@ -104,8 +117,12 @@ const useParamsController = () => { const [, setLogsStore] = useLogsStore(() => null); const [, setFilterStore] = useFilterStore((store) => store); - const { currentOffset, currentPage, perPage, rowNumber } = tableOpts; + const { currentOffset, currentPage, targetPage, perPage, headers, disabledColumns, targetColumns, rowNumber } = + tableOpts; + + const visibleHeaders = headers.filter((el) => !columnsToSkip.includes(el)); + const activeHeaders = visibleHeaders.filter((el) => !disabledColumns.includes(el)); const [searchParams, setSearchParams] = useSearchParams(); const syncRowNumber = useCallback((storeAsParams: Record, presentParams: Record) => { @@ -115,19 +132,34 @@ const useParamsController = () => { } } }, []); + const pageOffset = Math.ceil(currentOffset / perPage); useEffect(() => { const storeAsParams = storeToParamsObj({ timeRange, - offset: `${currentOffset}`, - page: `${currentPage}`, + page: `${targetPage ? targetPage : Math.ceil(currentPage + pageOffset)}`, view: viewMode, rows: `${perPage}`, query: custQuerySearchState.custSearchQuery, filterType: custQuerySearchState.viewMode, + fields: `${joinOrSplit(!_.isEmpty(targetColumns) ? targetColumns : activeHeaders)}`, rowNumber, }); const presentParams = paramsStringToParamsObj(searchParams); + if (storeAsParams.query !== presentParams.query) { + if (presentParams.filterType === 'filters') { + setFilterStore((store) => updateQuery(store, generateQueryBuilderASTFromSQL(presentParams.query) as QueryType)); + setFilterStore((store) => updateAppliedQuery(store, store.query)); + + setFilterStore((store) => setAppliedFilterQuery(store, presentParams.query)); + setFilterStore((store) => toogleQueryParamsFlag(store, true)); + } + setAppStore((store) => syncTimeRange(store)); + setLogsStore((store) => setCustQuerySearchState(store, presentParams.query, presentParams.filterType)); + } + + syncTimeRangeToStore(storeAsParams, presentParams); + if (['table', 'json'].includes(presentParams.view) && presentParams.view !== storeAsParams.view) { setLogsStore((store) => onToggleView(store, presentParams.view as 'table' | 'json')); } @@ -135,15 +167,27 @@ const useParamsController = () => { setLogsStore((store) => setPerPage(store, _.toNumber(presentParams.rows))); } - if (storeAsParams.query !== presentParams.query) { - setAppStore((store) => syncTimeRange(store)); - setLogsStore((store) => setCustQuerySearchState(store, presentParams.query, presentParams.filterType)); - if (presentParams.filterType === 'filters') - setFilterStore((store) => - applySavedFilters(store, generateQueryBuilderASTFromSQL(presentParams.query) as QueryType), + if (storeAsParams.fields !== presentParams.fields) { + setLogsStore((store) => setTargetColumns(store, joinOrSplit(presentParams.fields) as string[])); + } + + if (storeAsParams.page !== presentParams.page && !_.isEmpty(presentParams.page)) { + setLogsStore((store) => setTargetPage(store, _.toNumber(presentParams.page))); + + const offset = getOffset(_.toNumber(presentParams.page), _.toNumber(presentParams.rows)); + + if (offset > 0) { + setLogsStore((store) => setCurrentOffset(store, offset)); + + setLogsStore((store) => + setTargetPage( + store, + Math.abs(_.toNumber(presentParams.page) - Math.ceil(offset / _.toNumber(presentParams.rows))), + ), ); + } } - syncTimeRangeToStore(storeAsParams, presentParams); + syncRowNumber(storeAsParams, presentParams); setStoreSynced(true); }, []); @@ -152,31 +196,39 @@ const useParamsController = () => { if (isStoreSynced) { const storeAsParams = storeToParamsObj({ timeRange, - offset: `${currentOffset}`, - page: `${currentPage}`, + page: `${targetPage ? targetPage : Math.ceil(currentPage + pageOffset)}`, view: viewMode, rows: `${perPage}`, query: custQuerySearchState.custSearchQuery, filterType: custQuerySearchState.viewMode, + fields: `${joinOrSplit(!_.isEmpty(targetColumns) ? targetColumns : activeHeaders)}`, rowNumber, }); + const presentParams = paramsStringToParamsObj(searchParams); if (_.isEqual(storeAsParams, presentParams)) return; setSearchParams(storeAsParams); } - }, [tableOpts, viewMode, timeRange.startTime.toISOString(), timeRange.endTime.toISOString(), custQuerySearchState]); + }, [ + tableOpts, + targetPage, + viewMode, + timeRange.startTime.toISOString(), + timeRange.endTime.toISOString(), + custQuerySearchState, + ]); useEffect(() => { if (!isStoreSynced) return; const storeAsParams = storeToParamsObj({ timeRange, - offset: `${currentOffset}`, - page: `${currentPage}`, + page: `${targetPage ? targetPage : Math.ceil(currentPage + pageOffset)}`, view: viewMode, rows: `${perPage}`, query: custQuerySearchState.custSearchQuery, filterType: custQuerySearchState.viewMode, + fields: `${joinOrSplit(!_.isEmpty(targetColumns) ? targetColumns : activeHeaders)}`, rowNumber, }); const presentParams = paramsStringToParamsObj(searchParams); diff --git a/src/pages/Stream/providers/FilterProvider.tsx b/src/pages/Stream/providers/FilterProvider.tsx index c44c1b8a..c0b6a173 100644 --- a/src/pages/Stream/providers/FilterProvider.tsx +++ b/src/pages/Stream/providers/FilterProvider.tsx @@ -69,6 +69,7 @@ type FilterStore = { fieldTypeMap: FieldTypeMap; fieldNames: string[]; isSumbitDisabled: boolean; + isQueryFromParams: boolean; appliedQuery: QueryType; isSaveFiltersModalOpen: boolean; isSavedFiltersModalOpen: boolean; @@ -92,6 +93,7 @@ const initialState: FilterStore = { appliedFilterQuery: '', fieldTypeMap: {}, fieldNames: [], + isQueryFromParams: false, isSumbitDisabled: true, appliedQuery: defaultQuery, isSaveFiltersModalOpen: false, @@ -130,7 +132,9 @@ type FilterStoreReducers = { deleteRuleFromGroup: (store: FilterStore, groupId: string, ruleId: string) => ReducerOutput; updateGroupCombinator: (store: FilterStore, id: string, op: Combinator) => ReducerOutput; updateParentCombinator: (store: FilterStore, combinator: Combinator) => ReducerOutput; + updateAppliedQuery: (store: FilterStore, appliedQuery: QueryType) => ReducerOutput; updateRule: (store: FilterStore, groupId: string, ruleId: string, updateOpts: RuleUpdateOpts) => ReducerOutput; + updateQuery: (store: FilterStore, query: QueryType) => ReducerOutput; parseQuery: ( queryEngine: 'Parseable' | 'Trino' | undefined, query: QueryType, @@ -138,6 +142,7 @@ type FilterStoreReducers = { timeRangeOpts?: { startTime: Date; endTime: Date; timePartitionColumn: string }, ) => { where: string; parsedQuery: string }; toggleSubmitBtn: (store: FilterStore, val: boolean) => ReducerOutput; + toogleQueryParamsFlag: (store: FilterStore, val: boolean) => ReducerOutput; toggleSaveFiltersModal: (_store: FilterStore, val: boolean) => ReducerOutput; toggleSavedFiltersModal: (_store: FilterStore, val: boolean) => ReducerOutput; applySavedFilters: (store: FilterStore, query: QueryType) => ReducerOutput; @@ -177,6 +182,13 @@ const addRuleToGroup = (store: FilterStore, groupId: string) => { }; }; +const toogleQueryParamsFlag = (_store: FilterStore, val: boolean) => { + return { + ..._store, + isQueryFromParams: val, + }; +}; + const deleteRuleFromGroup = (store: FilterStore, groupId: string, ruleId: string) => { const { fields, query } = store; if (fields.length === 0) return {}; @@ -340,6 +352,20 @@ const toggleSavedFiltersModal = (_store: FilterStore, val: boolean) => { }; }; +const updateAppliedQuery = (store: FilterStore, appliedQuery: QueryType) => { + return { + ...store, + appliedQuery, + }; +}; + +const updateQuery = (store: FilterStore, query: QueryType) => { + return { + ...store, + query, + }; +}; + const applySavedFilters = (store: FilterStore, query: QueryType) => { return { ...store, @@ -358,11 +384,14 @@ const filterStoreReducers: FilterStoreReducers = { deleteRuleFromGroup, updateGroupCombinator, updateParentCombinator, + updateAppliedQuery, updateRule, + updateQuery, parseQuery, toggleSubmitBtn, toggleSaveFiltersModal, toggleSavedFiltersModal, + toogleQueryParamsFlag, applySavedFilters, setAppliedFilterQuery, }; diff --git a/src/pages/Stream/providers/LogsProvider.tsx b/src/pages/Stream/providers/LogsProvider.tsx index 98c1da9b..77a5d8e0 100644 --- a/src/pages/Stream/providers/LogsProvider.tsx +++ b/src/pages/Stream/providers/LogsProvider.tsx @@ -171,12 +171,14 @@ type LogsStore = { tableOpts: { disabledColumns: string[]; wrapDisabledColumns: string[]; + targetColumns: string[]; pinnedColumns: string[]; pageData: Log[]; totalPages: number; totalCount: number; displayedCount: number; currentPage: number; + targetPage: number | undefined; perPage: number; currentOffset: number; headers: string[]; @@ -228,6 +230,7 @@ type LogsStoreReducers = { setCurrentOffset: (store: LogsStore, offset: number) => ReducerOutput; setPerPage: (store: LogsStore, perPage: number) => ReducerOutput; setCurrentPage: (store: LogsStore, page: number) => ReducerOutput; + setTargetPage: (store: LogsStore, target: number | undefined) => ReducerOutput; setTotalCount: (store: LogsStore, totalCount: number) => ReducerOutput; setPageAndPageData: (store: LogsStore, pageNo: number, perPage?: number) => ReducerOutput; setAndSortData: (store: LogsStore, sortKey: string, sortOrder: 'asc' | 'desc') => ReducerOutput; @@ -250,6 +253,7 @@ type LogsStoreReducers = { onToggleView: (store: LogsStore, viewMode: 'json' | 'table') => ReducerOutput; toggleConfigViewType: (store: LogsStore) => ReducerOutput; setDisabledColumns: (store: LogsStore, columns: string[]) => ReducerOutput; + setTargetColumns: (store: LogsStore, columms: string[]) => ReducerOutput; setOrderedHeaders: (store: LogsStore, columns: string[]) => ReducerOutput; toggleWordWrap: (store: LogsStore) => ReducerOutput; setRowNumber: (store: LogsStore, rowNumber: string) => ReducerOutput; @@ -274,6 +278,7 @@ const initialState: LogsStore = { }, tableOpts: { + targetColumns: [], disabledColumns: [], wrapDisabledColumns: [], pinnedColumns: [], @@ -283,6 +288,7 @@ const initialState: LogsStore = { displayedCount: 0, totalPages: 0, currentPage: 0, + targetPage: undefined, currentOffset: 0, headers: [], orderedHeaders: [], @@ -454,6 +460,15 @@ const setDisabledColumns = (store: LogsStore, columns: string[]) => { }; }; +const setTargetColumns = (store: LogsStore, columns: string[]) => { + return { + tableOpts: { + ...store.tableOpts, + targetColumns: columns, + }, + }; +}; + const togglePinnedColumns = (store: LogsStore, columnName: string) => { const { tableOpts } = store; return { @@ -560,6 +575,15 @@ const setPerPage = (store: LogsStore, perPage: number) => { }; }; +const setTargetPage = (store: LogsStore, target: number | undefined) => { + return { + tableOpts: { + ...store.tableOpts, + targetPage: target ? target : undefined, + }, + }; +}; + const setCurrentPage = (store: LogsStore, currentPage: number) => { return { tableOpts: { @@ -879,6 +903,7 @@ const logsStoreReducers: LogsStoreReducers = { setStreamSchema, setPerPage, setCurrentPage, + setTargetPage, setCurrentOffset, setTotalCount, setPageAndPageData, @@ -900,6 +925,7 @@ const logsStoreReducers: LogsStoreReducers = { onToggleView, toggleConfigViewType, setDisabledColumns, + setTargetColumns, setOrderedHeaders, toggleWordWrap, toggleWrapDisabledColumns, diff --git a/src/utils/index.ts b/src/utils/index.ts index dae110da..2f8e36cf 100644 --- a/src/utils/index.ts +++ b/src/utils/index.ts @@ -105,3 +105,21 @@ export const copyTextToClipboard = async (value: any) => { return await navigator.clipboard.writeText(JSON.stringify(value, null, 2)); } }; + +export const getOffset = (page: number, rowSize: number) => { + const product = page * rowSize; + if (product % 1000 === 0) { + return Math.floor((product - 1) / 1000) * 1000; + } + + return Math.floor(product / 1000) * 1000; +}; + +export const joinOrSplit = (value: string[] | string): string | string[] => { + const joinOperator = ','; + if (Array.isArray(value)) { + return value.join(joinOperator); + } else { + return value.split(joinOperator); + } +};