React+Umi4使用状态管理器
序言
上一篇文章我们讲述了从零开始搭建一个Umi后台管理系统,本篇文章讲讲述如何使用状态管理器
项目的地址:github.com/XiaoRongwen...
教程开始
众所周知,Vue有Vuex/Pinia,React有Redux/Mobx,那Umi属于React系列,使用了什么呢?
翻开熟悉的Umi文档,一眼看去,哦,不知道!搜一下!搜完之后会发现umi内置了两种,分别是以下两种。 文档有说明,如果不是非常复杂的应用,选择useModel即可。

这里我的项目会使用useModel,emmm因为公司在用这个。但是我要先试用Dva,我就是要犯贱😍😍😍💕💕
如果你不想用Dva可直接跳转到下面useModel的内容
Dva(之前为类组件而生,现在函数组件不用,但是还是想研究试一下)
dva 首先是一个基于 redux 和 redux-saga 的数据流方案,然后为了简化开发体验,dva 还额外内置了 react-router 和 fetch,所以也可以理解为一个轻量级的应用框架。
- 官网dvajs.com/
- Umi使用链接umijs.org/docs/max/dv...

Umi中如何启用Dva
按照文档的我们可以自己去配置Dva
,也可以用指令去配置Dva,关于指令你可以去看Umi提供给的微生成器,它可以解决我们手动配置的问题。 为了能使用Umi的指令,我们需要全局安装Umi
npm install umi -g
能够使用umi命令之后我们开始按照文档来,使用微生成器帮我们生成。

执行 umi g dva
执行完成之后我们就会发现我们多了两个文件,一个是在config的配置文件,一个是模块文件count.ts
反正类似Vuex,不懂自己去研究下文档。不想写文档了~

在项目中调用Dva
在上面生成中多了一个count.ts,我们直接用这个来做事示例就好了。为了演示方便,我就在首页Home/index.tsx做演示了。文档说明这个适用于类组件,文档也是用类组件的,但是我们都已经是函数组件,就不再写类组件了。生成的coimt.ts会有一点问题,reducers函数中的写法不符合规范,不能直接+=,更改后的内容如下,换成了 return { ...state, num: state.num + 1 };
js
// eslint-disable-next-line no-promise-executor-return
const delay = (ms: number) => new Promise((res) => setTimeout(res, ms));
export default {
namespace: 'count',
state: {
num: 0,
},
reducers: {
add(state: any) {
console.log(111);
return { ...state, num: state.num + 1 };
},
},
effects: {
*addAsync(_action: any, { put }: any) {
yield delay(1000);
yield put({ type: 'add' });
},
},
};
使用步骤
按照文档,我们需要引入connect函数把模块和我们的组件tsx文件连接,然后使用props就可以访问,然后使用dispatch访问方法,执行函数修改数据,类似于vuex的dispatch和emit。,代码如下,详细讲解看下面截图。
js
import styles from './index.less';
import { trim } from '@/utils/format';
import Guide from '@/components/Guide';
import { Button } from 'antd';
import { PageContainer } from '@ant-design/pro-components';
import { useModel } from '@umijs/max';
// 状态管理
import { connect } from 'umi';
const HomePage = ({ dispatch, count }) => {
const { name } = useModel('global');
return (
<PageContainer ghost>
<div style={{ textAlign: 'center' }} className={styles.container}>
<Guide name={trim(name)} />
<h2>{count.num}</h2>
<Button
type="primary"
onClick={() => {
dispatch({ type: 'count/add' ,payload: {}});
}}
>
添加
</Button>
</div>
</PageContainer>
);
};
export default connect(({ count }) => ({
count,
}))(HomePage);

代码执行完成之后,我们去看页面,发现num初始值是0,我们也访问到了,然后们点击按钮添加,他就会执行add函数进行添加。
好了,大概就是这样,然后我们调用的add函数,其实dispath也能调用effects的函数
useModel
接下来我们使用useModel,其实我们创建完项目后,他们有给我们写好例子。 创建好项目的global.ts内容如下的,不知道是我写的还是项目带的,将就看一下很简单
js
// 全局共享数据示例
import { DEFAULT_NAME } from '@/constants';
import { useState } from 'react';
const useUser = () => {
const [name, setName] = useState<string>(DEFAULT_NAME);
return {
name,
setName,
};
};
export default useUser;
我们直接在上面讲的dva,home主页的组件中实践 这里直接调用了global的数据,然后调用函数改变数据
最后我们实践一下,内容如下

如果您有什么不懂得问题,可以去看项目,我放在github了。或者也可以私聊我。一起加油!!!!!!!!
下一篇umi主题定义
下一篇文章将讲述定义主题,持续关注,点赞,支持,才有动力更新啊