Dva 简介
- 借鉴 elm 的概念,Reducer,Effect 和 Subscription
- 框架,而非类库
- 基于 redux,react-router,redux-saga 的轻量级封装
Dva 的特性
- 仅有 5 个 API,其用法我们会在之后详细介绍。
- 支持 HMR,支持模块的热更新。
- 支持 SSR (ServerSideRender),支持服务器端渲染。
- 支持 Mobile/ReactNative,支持移动手机端的代码编写。
- 支持 TypeScript,支持 TypeScript,毋庸置疑这个会是 Javascript 的一个趋势。
- 支持路由和 Model 的动态加载。
Dva 的 5 个API
app = dva(Opts)
创建应用,返回 dva 实例(注:dva 支持多实例)。
在 opts
可以配置所有的 hooks
const app = dva({
history,
initialState,
onError,
onAction,
onStateChange,
onReducer,
onEffect,
onHmr,
extraReducers,
extraEnhancers,
});
这里比较常用的是,history 的配置,一般默认的是hashHistory
,如果要配置 history 为 browserHistory
,可以这样:
import createHistory from 'history/createBrowserHistory';
const app = dva({
history: createHistory(),
});
- 关于
react-router
中的hashHistory
和browserHistory
的区别大家可以看:react-router。 initialState
:指定初始数据,优先级高于model
中的state
,默认是{}
,但是基本上都在model
里面设置对应应的state
。
app.use(Hooks)
配置 hooks
或者注册插件。
这里最常见的就是 dva-loading 插件的配置,
import createLoading from 'dva-loading';
// ...
app.use(createLoading(opts));
但是一般对于全局的 loading
我们会根据业务的不同来显示相应不同的 loading
图标,我们可以根据自己的需要来选择注册相应的插件。
app.model(ModelObject)
这个是你数据逻辑处理,数据流动的地方。
modal
是 dva
里面与我们真正进行项目开发,逻辑处理,数据流动的地方。
这里面涉及到的 namespace
、Modal
、effects
和 reducer
等概念都很重要,我们会在接下来的部分详细讲解。
app.router(Function)
注册路由表,我们做路由跳转的地方。
一般都是通过下面的方式编写:
import { Router, Route } from 'dva/router';
app.router(({ history }) => {
return (
<Router history={history}>
<Route path="/" component={App} />
<Router>
);
});
但是如果你的项目特别的庞大,我们就要考虑到相应的性能的问题,但是入门可以先看一下这个。
解决性能问题,其实就是对路由进行按需加载,实现起来也比较简单,就是使用了 require.ensure
这个方法来帮我们实现,同时我们也可以使用 ES6 module
的动态 import
来实现按需加载。不过动态 import
这个方法还在提案中,我们需要接着 babel
插件来帮我们实现,具体笔者就不展开了。
app.start([HTMLElement], opts)
启动应用,将我们的应用跑起来。
Dva 九个概念
State(状态)
初始值,我们在 dva()
初始化的时候和在 model
里面的 state
对其两处进行定义,其中 model
中的优先级低于传给 dva()
的 opts.initialState
。
如下:
// dva()初始化
const app = dva({
initialState: { count: 1 },
});
// modal()定义事件
app.model({
namespace: 'count',
state: 0,
});
Action
表示操作事件,可以是同步,也可以是异步
action
的格式如下,它需要有一个 type
,表示这个 action
要触发什么操作;payload
则表示这个 action
将要传递的数据
{
type: String,
payload: data,
}
我们通过 dispatch
方法来发送一个 action
// Action
// Action 表示操作事件,可以是同步,也可以是异步
{
type: String,
payload: data
}
// 格式
dispatch(Action);
dispatch({ type: 'todos/add', payload: 'Learn Dva' });
其实我们可以构建一个 Action
创建函数,如下
function addTodo(text) {
return {
type: ADD_TODO,
text
}
}
//我们直接dispatch(addTodo()),就发送了一个action。
dispatch(addTodo())
action 更多内容可以查看文档:redux——action
Model
model
是 dva 中最重要的概念,Model
非 MVC
中的 M,而是领域模型,用于把数据相关的逻辑聚合到一起,几乎所有的数据,逻辑都在这边进行处理分发
state
这里的 state
跟我们刚刚讲的 state 的概念是一样的,只不过它的优先级比初始化的低,但是基本上项目中的 state
都是在这里定义的。
namespace
model 的命名空间,同时也是他在全局 state 上的属性,只能用字符串,我们在发送 action 到相应的 reducer 时,就会需要用到 namespace
。
Reducer
以 key/value
格式定义 reducer
,用于处理同步操作,唯一可以修改 state
的地方。由 action
触发。其实一个纯函数。
Effect
用于处理异步操作和业务逻辑,不直接修改 state
,简单的来说,就是获取从服务端获取数据,并且发起一个 action
交给 reducer
的地方。
其中它用到了redux-saga
,里面有几个常用的函数。
*add(action, { call, put }) {
yield call(delay, 1000);
yield put({ type: 'minus' });
},
在项目中最主要的会用到的是 put
与 call
。
Subscription
subscription
是订阅,用于订阅一个数据源,然后根据需要 dispatch
相应的 action。
在 app.start()
时被执行,数据源可以是当前的时间、当前页面的 url、服务器的 websocket
连接、history
路由变化、键盘事件等等。
Router
Router 表示路由配置信息,项目中的 router.js。
export default function({ history }){
return(
<Router history={history}>
<Route path="/" component={App} />
</Router>
);
}
RouteComponent
RouteComponent
表示 Router
里匹配路径的 Component,通常会绑定 model
的数据。如下:
import { connect } from 'dva';
function App() {
return <div>App</div>;
}
function mapStateToProps(state) {
return { todos: state.todos };
}
export default connect(mapStateToProps)(App);
整体架构
我简单的分析一下这个图:
首先我们根据 url
访问相关的 Route-Component
,在组件中我们通过 dispatch
发送 action
到 model
里面的 effect
或者直接 Reducer
。
当我们将 action
发送给 Effect
,基本上是取服务器上面请求数据的,服务器返回数据之后,effect
会发送相应的 action
给 reducer
,由唯一能改变 state
的 reducer
改变 state
,然后通过 connect
重新渲染组件。
当我们将 action
发送给 reducer
,那直接由 reducer
改变 state
,然后通过 connect
重新渲染组件。
这样我们就能走完一个流程了。
umi与 dva 和 doadhog 的关系
以下比较引自官网:
roadhog
是基于webpack
的封装工具,目的是简化webpack
的配置umi
可以简单地理解为roadhog
+ 路由,思路类似next.js/nuxt.js
,辅以一套插件机制,目的是通过框架的方式简化React
开发dva
目前是纯粹的数据流,和umi
以及roadhog
之间并没有相互的依赖关系,可以分开使用也可以一起使用,更多可以参考:使用 umi 改进 dva 项目开发
参考链接
- umi 官网
- roadhog介绍
- dva 官网
- webpack4.0 学习文档
- Dva-React 应用框架在蚂蚁金服的实践
- 10分钟 让你dva从入门到精通
- 基于dva-cli&antd的react项目实战
示例代码
- dva-demo 项目示例代码
- umi-demo 项目示例代码
常见问题FAQ
- 免费下载或者VIP会员专享资源能否直接商用?
- 本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
- 提示下载完但解压或打开不了?
- 找不到素材资源介绍文章里的示例图片?
- 模板不会安装或需要功能定制以及二次开发?
发表评论
还没有评论,快来抢沙发吧!