在react项目中,使用react+umi+dva+antd这一阿里系列技术栈的人越来越多,本文主要讲在umi中使用dva的过程
一、前言
在实际的前端开发中我们希望把数据逻辑和视图逻辑分开管理在不同的模块中,使得代码更加健壮,同时易于调试。
我们希望这些数据在需要的时候,可以提供给不同的组件使用:也即数据共享。
而 dva 就是用来满足这些需求的:
通过把状态上提到 dva model 中,我们把数据逻辑从页面中抽离出来。
通过 effect 优雅地处理数据生成过程中的副作用,副作用中最常见的就是异步逻辑。
dva model 中的数据可以注入给任意组件。
另外,dva 允许把数据逻辑再拆分(「页面」常常就是分隔的标志),以 namespace 区分。当你觉得有必要时,不同的 namespace 之间的 state 是可以互相访问的。
二 、主要对象介绍
dva 的 model 对象有几个基本的属性,需要掌握:
namespace:model 的命名空间,只能用字符串。一个大型应用可能包含多个 model,通过namespace区分。
state:当前 model 状态的初始值,表示当前状态。
reducers:用于处理同步操作,唯一可以修改 state的地方,由 action 触发。reducer 是一个纯函数,它接受当前的 state 及一个 action 对象。action 对象里面可以包含数据体(payload)作为入参,需要返回一个新的 state。
effects:用于处理异步操作(例如:与服务端交互)和业务逻辑,也是由 action 触发。但是,它不可以修改 state,要通过触发 action 调用 reducer 实现对 state 的间接操作。
action:是 reducers 及 effects 的触发器,一般是一个对象,形如{ type: ‘add’, payload: todo },通过 type 属性可以匹配到具体某个 reducer 或者 effect,payload 属性则是数据体,用于传送给 reducer 或 effect。
三、简单使用
- 在umi项目 src目录下新建 models 目录(规定全局名称必须models)
如下,我这里新建了个system.js文件 (名称随便取)
代码如下:
export default {
// models命名空间,需全局唯一
namespace: 'system',
// models存储的数据store
state: {
dataList: 1
},
// 更新store,用新数据合并state的旧数据
reducers: {
save(state, { payload }) {
return { ...state, ...payload };
}
},
};
在组件中进行使用
import React from 'react';
import { connect } from 'dva'
const hello = (props) => {
const btnFn = async () =>{
// 通过dispatch 调用文件下的save 改变dva 下 system 的 state的状态值
props.dispatch({
type: 'system/save', // type,命名空间/reducers方法名
payload: {
dataList: props.system.dataList+1 // payload,参数
}
})
}
return (
<div>
<button onClick={ btnFn }>点击</button>
{ props.system.dataList }
</div >
)
}
// 建立组件与dva的连接
export default connect(({ system }) => ({ system }))(hello);
这样直接使用就可以获取到dav system下存的state状态值了,并通过连接进行修改
我这里目前暂时没写其它使用,主要针对刚开始使用dva,对里面的state状态数据进行操控
四、关于connect
connect 方法返回的也是一个 React 组件,通常称为容器组件。因为它是原始 UI 组件的容器,即在外面包了一层 State。connect 方法传入的第一个参数是 mapStateToProps 函数,该函数需要返回一个对象,用于建立 State 到 Props 的映射关系。
简而言之,connect的作用是将组件和models结合在一起。将models中的state绑定到组件的props中。并提供一些额外的功能,譬如dispatch建立组件与dva的连接通道
connect的连接方式有很多种
import React from 'react';
import { connect } from 'dva';
const hello = (props) => {
return (
<div>
</div >
)
}
export default connect(({ system }) => ({ system }))(hello);
import React from 'react';
import { connect } from 'dva';
connect(({ system }) => ({ system }))
const hello = (props) => {
console.log(props)
return (
<div>
2
</div >
)
}
export default hello;
3.使用ts的情况下
import React from 'react';
import { connect } from 'dva';
@connect(({ system }) => ({ system }))
const hello = (props:any) => {
console.log(props)
return (
<div>
dva
</div >
)
}
export default hello;
其实还有很多种,后续再更新哈,这篇文章只针对基础的,后续还会写篇进阶的