diff --git a/eslint.config.mjs b/eslint.config.mjs index 27db3f4..e4f027c 100644 --- a/eslint.config.mjs +++ b/eslint.config.mjs @@ -13,7 +13,13 @@ import eslint from '@eslint/js'; export default defineConfig([ ...pluginQuery.configs['flat/recommended'], tseslint.config(eslint.configs.recommended, tseslint.configs.recommended), - globalIgnores(['node_modules/*', 'dist/*', 'docs/*', '**/coverage']), + globalIgnores([ + 'node_modules/*', + 'dist/*', + 'docs/*', + '**/coverage', + 'storybook-static/*', + ]), fecPlugin, reactHooks.configs['recommended-latest'], jsdoc.configs['flat/recommended'], diff --git a/src/utilities/hooks/useQueryWithUtilities/hooks/useParamsFromTableState.js b/src/utilities/hooks/useQueryWithUtilities/hooks/useParamsFromTableState.js index db1a535..0f35e47 100644 --- a/src/utilities/hooks/useQueryWithUtilities/hooks/useParamsFromTableState.js +++ b/src/utilities/hooks/useQueryWithUtilities/hooks/useParamsFromTableState.js @@ -2,7 +2,16 @@ import { useDeepCompareMemo } from 'use-deep-compare'; import { useSerialisedTableState } from '~/hooks'; -const useParamsFromTableState = ({ paramsOption, useTableState }) => { +const defaultCombine = (tableParams, optionParams) => ({ + ...(tableParams || {}), + ...(optionParams || {}), +}); + +const useParamsFromTableState = ({ + paramsOption, + useTableState, + combineParamsWithTableState = defaultCombine, +}) => { const serialisedTableState = useSerialisedTableState(); const params = useDeepCompareMemo(() => { @@ -15,15 +24,18 @@ const useParamsFromTableState = ({ paramsOption, useTableState }) => { } : undefined; - // TODO There may be issues here if for example there is a filter passed via the paramsOption - // We should maybe have a "combineWithTableState" option to pass in a "transforming" function - const combinedParams = { - ...(tableStateParams ? tableStateParams : {}), - ...(paramsOption ? paramsOption : {}), - }; + const combinedParams = combineParamsWithTableState( + tableStateParams, + paramsOption, + ); return Object.keys(combinedParams).length ? combinedParams : undefined; - }, [serialisedTableState, useTableState, paramsOption]); + }, [ + serialisedTableState, + useTableState, + paramsOption, + combineParamsWithTableState, + ]); return params; }; diff --git a/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.js b/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.js index 6590e06..7f89580 100644 --- a/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.js +++ b/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.js @@ -16,10 +16,12 @@ const useQueryWithUtilities = ({ queue, tableQueries: tableQueriesOptions, totalBatched: totalBatchedOptions, + combineParamsWithTableState, } = {}) => { const params = useParamsFromTableState({ paramsOption, useTableState, + combineParamsWithTableState, }); const queryClient = useQueryClient(); @@ -32,8 +34,14 @@ const useQueryWithUtilities = ({ [queryKeyOption, params], ); const queryFn = useCallback( - async (queryFnParams) => await fetchFn({ ...params, ...queryFnParams }), - [fetchFn, params], + async (queryFnParams) => { + if (combineParamsWithTableState) { + const finalParams = combineParamsWithTableState(params, queryFnParams); + return await fetchFn(finalParams); + } + return await fetchFn({ ...params, ...queryFnParams }); + }, + [fetchFn, params, combineParamsWithTableState], ); const { diff --git a/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.stories.js b/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.stories.js index a0b0d8f..3bf6c32 100644 --- a/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.stories.js +++ b/src/utilities/hooks/useQueryWithUtilities/useQueryWithUtilities.stories.js @@ -254,3 +254,81 @@ export const QueryQueueStory = { }; export default meta; + +const TableQueriesWithCombinedFiltersExample = () => { + const fetchFn = useCallback( + async (params) => await restApi('/api', params), + [], + ); + + const combineParamsWithTableState = useCallback( + (tableStateParams, additionalParams) => { + const tableFilters = tableStateParams?.filters; + const optionFilters = additionalParams?.filters; + + const combinedParams = { + ...(tableStateParams ? tableStateParams : {}), + ...(additionalParams ? additionalParams : {}), + }; + if (tableFilters && optionFilters) { + combinedParams.filters = `${tableFilters} and ${optionFilters}`; + } + return combinedParams; + }, + [], + ); + + const { + loading, + result: { data, meta: { total } = {} } = {}, + error, + exporter, + itemIdsInTable, + itemIdsOnPage, + } = useQueryWithUtilities({ + fetchFn, + useTableState: true, + params: { + filters: '(.rating >= 3)', + }, + combineParamsWithTableState, + }); + + return ( + <> + +

+
+ + + ); +}; + +export const TableQueriesWithCombinedFiltersStory = { + decorators: [ + (Story) => ( + + + + + + ), + ], + render: (args) => , +};