/** * @license * Copyright Stbui All Rights Reserved. * https://github.com/stbui/prophet */ import { isValidElement, useMemo, useEffect } from 'react'; import { useListParams } from './useListParams'; import { useGetList } from '../dataProvider'; import useVersion from './useVersion'; import { useNotify } from '../sideEffect'; export interface ListProps { resource: string; basePath: string; hasCreate?: boolean; filterDefaultValues?: object; sort?: any; perPage?: number; filter?: object; debounce?: number; [key: string]: any; } export interface ListControllerProps { resource: string; basePath: string; data: any; ids: any; currentSort: any; total: number; hasCreate: any; page: number; perPage: number; filterValues: any; displayedFilters: any; setFilters: (filters: any, displayedFilters: any) => void; hideFilter: (filterName: string) => void; showFilter: (filterName: string, defaultValue: any) => void; setPage: (page: number) => void; setPerPage: (page: number) => void; setSort: (sort: string) => void; loading: any; loaded: any; version: number; } /** * * @param {object} props * * @return {Object} * * @example * * import { useListController } from '@stbui/prophet-core'; * import ListView from './ListView'; * * const List = props => { * const controllerProps = useListController(props); * return ; * } * */ export const useListController = (props: ListProps): ListControllerProps => { const { resource, basePath, hasCreate, filterDefaultValues, filter, sort = { field: 'id', order: 'ASC' }, perPage = 10, debounce = 500, } = props; if (filter && isValidElement(filter)) { throw new Error('...'); } const version = useVersion(); const notify = useNotify(); const [query, queryMethod] = useListParams({ resource, filterDefaultValues, sort, perPage, debounceTime: debounce, }); const { data, ids, total, loading, loaded } = useGetList( resource, { page: query.page, perPage: query.perPage, }, { ...query.filter, ...filter }, { field: query.sort, order: query.order }, { version, onFailure: error => notify( typeof error === 'string' ? error : error.message || 'prophet.notification.http_error', 'error' ), } ); useEffect(() => { if ( query.page <= 0 || (!loading && query.page > 1 && (ids || []).length === 0) ) { queryMethod.setPage(1); } }, [loading, query.page, ids, queryMethod]); const currentSort = useMemo( () => ({ field: query.sort, order: query.order, }), [query.sort, query.order] ); return { resource, basePath, data, ids: ids || [], currentSort, total: total != undefined ? total : 0, hasCreate, page: query.page, perPage: query.perPage, filterValues: query.filterValues, displayedFilters: query.displayedFilters, setFilters: queryMethod.setFilters, hideFilter: queryMethod.hideFilter, showFilter: queryMethod.showFilter, setPage: queryMethod.setPage, setPerPage: queryMethod.setPerPage, setSort: queryMethod.setSort, loading, loaded, version, }; }; export default useListController;