react: typescript custom hooks useAsyncTable

define basic data:

const SET_QUERY = "SET_QUERY";
const TOGGLE_LOADING = "TOGGLE_LOADING";
const SET_PAGINATION = "SET_PAGINATION";
const SET_TABLE_DATA = "SET_TABLE_DATA";
const SET_DATA_SOURCE = "SET_DATA_SOURCE";
const initialPagination = {page: 0, size: 10};

declare reducer:

const tableReducer = (state: any, action: any) => {
  const {payload} = action;
  switch(state.type) {
     case TOGGLE_LOADING: 
        return {...state, loading: !state.loading};
    case SET_QUERY:
        return {...state, params: payload.params, pagination: initialPagination};
    case SET_PAGINATION:
       return {...state, pagination: payload.pagination};
    case SET_DATA_SOURCE:
      return {...state, dataSource: payload.dataSource};
    case SET_TABLE_DATA:
      return {...state, pagination: payload.pagination, dataSource: payload.dataSource};
     default:
       return state
  }
}

define useAsyncTable

传入相应的参数,通过userReducer执行不一样的action更新state数据,使用useEffect监听数据发生变化重新渲染页面

function useAsyncTable (columns: [], searchParams: any =null, queryAction: any, listName: string){
  const queryParams:any = null;
  const dataSource any[] = [];
  const initialState = {
    loading: false,
    queryParams: queryParams,
    dataSource: dataSource
  }
  const [state, dispatch] = useReducer(tableReducer, initialState);
  const handlePageChange = (pageNum: number) => {
    dispatch(type: SET_PAGINATION, payload: {...state.pagination, page: pageNum - 1});
  }
  const onQuery = () => {
    dispatch({type: TOOGLE_LOADING});
    queryAction({...state.params, ...pagination})
         .then((res: any) => {
             const {totalElements} = res.data;
             dispatch({type: TOOGLE_LOADING});
             dispatch({type: SET_TABLE_DATA, payload: {
                 pagination: {...state.pagination, total: totalElements}
                 dataSource: res.data[listName]
             }})
          })
         .catch(() => {
             dispatch({type: TOOGLE_LOADING});
          })
  }
}

useEffect 监听请求

useEffect(()=>{
     if (searchParams && JSON.Stringfy(searchParams) !== JSON.Stringfy(state.queryParams) ) {
       dispatch({type: SET_QUERY, payload: {
           params: searchParams
       }})
    } else {
        onQuery()
    }
},[searchParams, state.pagination.page, state.query])

return renderer:

return (
   <>
      <Table
           rowKey={(record: any, index: any) => index}
           className= " table-list"
           columns={columns}
           loading={state.loading}
           dataSource={state.dataSource}
           pagination={false}
       />
    <AppPagination
         total={state.pagination.total}
         pageSize={state.pagination.page + 1}
         total={state.pagination.
         handleChangePage={handleChangePage)}
    />
  </> )

简单调用:

const queryAction = (params: ISearchParams) => {
    return Promise method
}
const tableList = useAsyncTable(columns, searchParams, queryAction);

return (<>{tableList}</>)    
原文地址:https://www.cnblogs.com/Nyan-Workflow-FC/p/11248648.html