• 效果展示

  • 导入
yarn add @ant-design/pro-table
//使用DatePicker时间选择器
yarn add moment
  • 创建user模块

  • 配置路由及配置代理
在.umire.ts中import { defineConfig } from 'umi';export default defineConfig({nodeModulesTransform: {type: 'none',},routes: [{ path: '/', component: '@/pages/users/index' },],fastRefresh: {},proxy: {'/api': {'target': 'https://www.fastmock.site/mock/fed13828390069db6c28fe3f2da98a19/demo1/',// 'target': 'https://public-api-v1.aspirantzhang.com/','changeOrigin': true,'pathRewrite': { '^/api': '' },},},
});
  • 封装网络请求request.ts
/** Request 网络请求工具 更详细的 api 文档: https://github.com/umijs/umi-request */
import { extend } from 'umi-request';
import { message } from 'antd';const codeMessage: { [status: string]: string } = {200: '服务器成功返回请求的数据。',201: '新建或修改数据成功。',202: '一个请求已经进入后台排队(异步任务)。',204: '删除数据成功。',400: '发出的请求有错误,服务器没有进行新建或修改数据的操作。',401: '用户没有权限(令牌、用户名、密码错误)。',403: '用户得到授权,但是访问是被禁止的。',404: '发出的请求针对的是不存在的记录,服务器没有进行操作。',406: '请求的格式不可得。',410: '请求的资源被永久删除,且不会再得到的。',422: '当创建一个对象时,发生一个验证错误。',500: '服务器发生错误,请检查服务器。',502: '网关错误。',503: '服务不可用,服务器暂时过载或维护。',504: '网关超时。',
};/** 异常处理程序 */
const errorHandler = (error: { response: Response }): Response => {const { response } = error;if (response && response.status) {const errorText = codeMessage[response.status] || response.statusText;message.error(errorText);} else if (!response) {message.error('您的网络发生异常,无法连接服务器');}return response;
};/** 配置request请求时的默认参数 */
const request = extend({errorHandler, // 默认错误处理credentials: 'include', // 默认请求是否带上cookie
});// request拦截器, 改变url 或 options.
request.interceptors.request.use((url, options) => {console.log(url)if (options.data) {console.log(JSON.stringify(options.data))} else if (options.params && Object.keys(options.params).length > 0) {console.log(options.params)}return {url: url,options: options,};
});// response拦截器, 处理response
request.interceptors.response.use(async response => {const data = await response.clone().json();console.log(data)if (data.code !== 200) {message.error(data.message);return data.message} else {return response;}
});
export default request;
  • 网络请求接口(service.ts中)

import { request as request1 } from 'umi';
import { message } from 'antd';import request from '@/utils/request';import { FormValues } from './data'export async function getRemoteList1() {return request1('/api/users', {method: 'get'}).then(response => {return response}).catch(error => {console.log(error);});
}export async function editRecord1({ id, value }: any) {return request1(`/api/edit`, {method: 'post',data: value}).then(response => {if (response.code != 200) {message.error(response.message);}return response}).catch(error => {message.error(error);});
}// -----------------------------------使用封装后的request---------------------------------------------type EditRecordParamsType = {id: number | undefined;value: FormValues;
};export async function getRemoteList(params: {pageSize: number, current: number, id?: string,startTime?: string, endTime?: string
}): Promise<any> {console.log("getRemoteList==>" + params.current + ",----" + params.pageSize+ ",----" + params.id + ",----" + params.startTime + ",----" + params.endTime)return request('/api/users');
}export async function editRecord(params: EditRecordParamsType): Promise<any> {return request('/api/edit', {method: 'POST',data: params,});
}
  • 提取公用数据类型(data.d.ts中)
/*** 这个文件是放 公共的 类型接口的*/import { Key } from "react"/*** 封装后台返回的数据*/
export type SingleUserType ={id: number,name?: string,email?: string,create_time?: string,update_time?: string,status: number
}/*** Modal 框的确定按钮的类型*/
export type FormValues ={[name: string]: any
}
  • 首页index.tsx展示数据
import React, { useState, useRef, FC } from 'react';import { PlusOutlined } from '@ant-design/icons';
import { Space, message, Button } from 'antd';
import ProTable from '@ant-design/pro-table';import UserModal from './components/UserModal'
import { SingleUserType, FormValues } from './data'
import type { ProColumns, ActionType } from '@ant-design/pro-table';
import { editRecord, getRemoteList } from './service'type ListParamsType = {pageSize: number,current: number,id?: string,startTime?: string,endTime?: string
}const UserListPage: FC<any> = () => {//控制modal弹框const [visible, setVisible] = useState(false);const [confirmLoading, setConfirmLoading] = useState(false);const [record, setRecord] = useState<SingleUserType | undefined>(undefined);//配置ProTableconst ref = useRef<ActionType>();//编辑const onClickEdit = (record: SingleUserType) => {setVisible(true)setRecord(record)};/*** 表单提交*/const onFinish = async (value: FormValues) => {setConfirmLoading(true);const id = record?.idconst result = await editRecord({ id, value })if (result && result instanceof Object) {message.success(result.data);setVisible(false);// 刷新ref.current?.reload();}setConfirmLoading(false);};/*** ProTable的网络请求 request*/const requestHandler = async (params: ListParamsType) => {console.log(params)const users = await getRemoteList(params);return {data: users.data,success: true,total: users.meta?.total}}//关闭弹窗const handleCancel = () => {setVisible(false);};const columns: ProColumns<SingleUserType>[] = [{title: 'ID',dataIndex: 'id',width: 68,},{title: '名称',dataIndex: 'name',search: false,ellipsis: true,render: (text) => <a>{text}</a>,},{title: '创建时间',key: 'showTime',dataIndex: 'create_time',valueType: 'dateTime',hideInSearch: true,},{title: '创建时间',dataIndex: 'create_time',valueType: 'dateTimeRange',hideInTable: true,colSize:2,search: {transform: (value) => {console.log(value)return {startTime: value[0],endTime: value[1],};},},},{title: '操作',render: (text, record: SingleUserType) => (<Space size="middle"><a onClick={() => onClickEdit(record)}>编辑</a><a>删除</a></Space>),},];return (<div className="list-table"><ProTable request={requestHandler}actionRef={ref}columns={columns}rowKey="id"// search={false}search={{labelWidth: 'auto',}}pagination={{showQuickJumper: true,pageSize: 10,}}form={{// 由于配置了 transform,提交的参与与定义的不同这里需要转化一下syncToUrl: (values, type) => {if (type === 'get') {return {...values,create_time: [values.startTime, values.endTime],};}return values;},span:4}}toolBarRender={() => [<Button key="button" icon={<PlusOutlined />} type="primary">新建</Button>]}/><UserModal visible={visible} confirmLoading={confirmLoading}onFinish={onFinish} //关联子组件方法handleCancel={handleCancel}record={record} /></div>)
}export default UserListPage
  • 弹窗UserModal.tsx
import React, { useEffect, FC } from 'react'
import { Modal, Form, Input, DatePicker ,Switch } from 'antd';
import moment from 'moment';import { SingleUserType, FormValues } from '../data'/*** 声明下方 props 类型* const { visible, confirmLoading, record, handleCancel, onFinish } = props*/
type userModalProps = {visible: boolean,confirmLoading: boolean,record: SingleUserType | undefined,handleCancel: () => void,onFinish: (values: FormValues) => void
}const UserModal: FC<userModalProps> = (props) => {const { visible, confirmLoading, record, handleCancel, onFinish } = propsconst [form] = Form.useForm();//相当于componentDidMountuseEffect(() => {if (record == undefined) {form.resetFields()} else {//普通输入框// form.setFieldsValue(record);//处理DatePickerform.setFieldsValue({...record,create_time:moment(record.create_time),status:record.status===1?true:false})}}, [visible])//点击弹窗const handleOk = () => {form.submit()};/*** 表单失败*/const onFinishFailed = (err: any) => {console.log(err)};return (<div><Modaltitle="Title"forceRendervisible={visible}okText='确定'cancelText="取消"onOk={handleOk}//传递父组件处理confirmLoading={confirmLoading}onCancel={handleCancel}//传递父组件处理><Formform={form}name="basic"onFinish={onFinish}onFinishFailed={onFinishFailed}><Form.Itemlabel="name"name="name"rules={[{ required: true, message: '请输入name' }]}><Input /></Form.Item><Form.Itemlabel="CreateTime"name="create_time"rules={[{ required: true, message: '请选择create_time' }]}><DatePicker showTime /></Form.Item><Form.Itemlabel="status"name="status"valuePropName="checked"rules={[{ required: true, message: '请输入status' }]}><Switch  /></Form.Item></Form></Modal></div>)
}export default UserModal;

umi.js学习(八)、案例三、ProTable 简单使用相关推荐

  1. umi.js学习(一)、认识umi.js

    umi.js安装 npm install -g umi 查看umi.js版本 umi -v 创建umi项目 先找个地方建个空目录. $ mkdir myapp && cd myapp ...

  2. 【Node.js学习小案例】DNS域名解析 一

    Node.js 百度百科: Node.js 是一个基于Chrome JavaScript 运行时建立的一个平台, 用来方便地搭建快速的 易于扩展的网络应用· Node.js 借助事件驱动, 非阻塞I/ ...

  3. node.js(node.js+mongoose小案例)_实现简单的注册登录退出

    一.前言 通过node.js基本知识对node.js基本知识的一个简单应用 1.注册 2.登录 3.退出 二.基本内容 1.项目结构搭建如图所示 2.这个小案列中用到了art-template子模板以 ...

  4. 设计模式学习笔记(三)简单工厂、工厂方法和抽象工厂之间的区别

    设计模式中的工厂模式(Factory Design pattern)是一个比较常用的创建型设计模式,其中可以细分为三种:简单工厂(Simple Factory).工厂方法(Factory Method ...

  5. 原生JS仿造华为商城案例-实现了简单页面-两种轮播图思路的实现-动态展示数据

    文章目录 功能简介 项目准备 项目说明 方案一:源代码 CSS样式 HTML结构 JS逻辑 方案二:源代码 CSS样式 HTML结构 JS逻辑 功能简介 页面展示 该项目功能实现: 无限滚动轮播图 j ...

  6. Vue.js学习笔记(三):隐藏a标签鼠标悬浮状态下浏览器左下角出现的链接地址

    前言 当a标签悬浮时浏览器左下角会出现链接地址,为了隐藏链接地址,除了使用用点击事件代替以外,我们还可以一次性解决页面所有a标签悬浮出现链接的问题. mounted() {this.deleteMsg ...

  7. JS 作用域与变量提升---JS 学习笔记(三)

    你知道下面的JavaScript代码执行时会输出什么吗? var foo = 1; function bar() {if (!foo) {var foo = 10;}console.log(foo); ...

  8. Vue.js学习系列(三十四)-- Vue.js样式绑定(五)

    2019独角兽企业重金招聘Python工程师标准>>> 2. Vue.js style(内联样式) 我们可以在 v-bind:style 直接设置样式: <!DOCTYPE h ...

  9. js学习总结----案例之多级菜单js版本

    具体代码如下: <!DOCTYPE html> <html lang="en"> <head><meta charset="UT ...

最新文章

  1. 谷歌发布史上最强人类大脑「地图」,在线可视3D神经元「森林」!
  2. 卷组删除pv_Linux LVM(逻辑卷管理)的删除
  3. c语言编译器怎么用scanfkl,C语言一些笔记
  4. pygame碰撞检测
  5. [2020-11-28 contest]素数(数学),精灵(区间dp),农夫约的假期(结论),观察(树链剖分lca+set)
  6. 结构体跨函数应用(二)
  7. ASP.NET 页面生存周期概览
  8. linux字符设备驱动在哪里设置,从点一个灯开始学写Linux字符设备驱动!
  9. 字更大、页面更简单 淘宝长辈模式正式上线
  10. 让读者快速了解RocketMQ消息中间件需要解决哪些问题
  11. intellij idea 12 搭建maven web项目 freemarker + spring mvc
  12. angularjs sill 创建项目_AngularJS快速上手,从安装到运行
  13. ghpython_根据曲线曲率向量和切向量绘制椭圆
  14. Typec接口颜色代表什么?
  15. Android开发跳坑之路
  16. 解决win10没Wifi功能了,无线网卡驱动异常代码56的问题
  17. SOCKET - 实现任意 HTTPS 站点代理, 支持篡改内容
  18. 成功_专业_社交_意识
  19. 机顶盒ttl无法输入_中兴盒子连接TTL线后无法输入代码、不跑码乱码的解决方法分享...
  20. ocx 访问 html,HTML 加载ocx VB编写的控件

热门文章

  1. Lucene 5.2.1 + jcseg 1.9.6中文分词索引(Lucene 学习序列2)
  2. Android8.0未知来源应用安装权限最好的适配方案
  3. Wilcoxon符号秩检验-MATLAB实现
  4. plotplay恢复默认设置_PotPlayer播放器常用设置
  5. pcieport 0000:00:1.0:AER: PCIe Bus Error: severity=Corrected--解决ubuntu磁盘爆满导致无法开机问题
  6. STM32—时钟树(结合系统时钟函数理解)
  7. 一个整数有几个奇数几个偶数字
  8. Android 手机卫士(1)
  9. Google Developer Day 2016见闻
  10. 关于Keil出现Browse Information of one or more files is not avaliable