DvaJS快速上手

一、DvaJS 介绍

dva 首先是一个基于 reduxredux-saga 的数据流方案,然后为了简化开发体验,dva 还额外内置了 react-routerfetch,所以也可以理解为一个轻量级的应用框架。

特性

  • 易学易用
    仅有 6 个 api,对 redux 用户尤其友好,配合 umi 使用 后更是降低为 0 API
  • elm 概念
    通过 reducers, effectssubscriptions 组织 model
  • 插件机制
    比如 dva-loading 可以自动处理 loading 状态,不用一遍遍地写 showLoadinghideLoading
  • 支持 HMR
    基于 babel-plugin-dva-hmr 实现 componentsroutesmodels 的 HMR

二、DvaJS 使用

1.安装 dva-cli

$ cnpm install -g dva-cli

安装成功之后查看 dva 版本

$ dva -v

2.创建新应用

$ dva new dva-app

创建成功后进入 dva-app 目录

$ cd dva-app

并启动开发服务器

$ npm start

3.使用 antd

$ cnpm install --save antd babel-plugin-import

编辑 .webpackrc ,使 babel-plugin-import 插件生效

{
+  "extraBabelPlugins": [
+    ["import", { "libraryName": "antd", "libraryDirectory": "es", "style": "css" }]
+  ]
}

三、示例

article.js

//[src/models/article.js]
//article的model
import {findArticle} from '../services/article';
export default {

  namespace: 'article',

  state: {
      msg:'hello',
      articleData:[]
  },

  //异步action
  effects: {
    //payload: action.payload
    //call 调用service文件夹中的方法 service是异步请求
    //put: 转发action
    *getData1({ payload }, { call, put }){
      //call 第一个参数是service层的方法,第二个参数是service层方法需要的数据
      let res = yield call(findArticle, payload);
      yield put({type:'changeArticleData',payload:res.data.list})
    }
  },

  //同步action
  reducers: {
    //changeMsg就是action的type
    changeMsg1(state,action){
      return {
        ...state,
        msg:action.payload
      }
    },
    changeArticleData(state,action){
      return {
        ...state,
        articleData:action.payload
      }
    }
  },
};

index.js

//[src/models/index.js]
const context = require.context('./', false, /\.js$/);
export default context
  .keys()
  .filter(item => item !== './index.js')
  .map(key => context(key));

Article.js

//[src/routes/Article.js]
import React, { Component } from 'react';
import {Button} from 'antd';
import {connect} from 'dva';
class Article extends Component {
    render() {
        return (
            <div>
                hello
                {JSON.stringify(this.props.article)}
                <Button type="primary" onClick={this.props.changeMsg}>更改同步数据</Button>
                <Button type="primary" onClick={this.props.getData}>获取异步数据</Button>
            </div>
        );
    }
}

const mapDispatchToProps = (dispatch, ownProps) => {
    return {
        changeMsg: () => {
            //分发action 分发到article命名空间底下的action
            dispatch({type:'article/changeMsg1',payload:'111'});
        },
        getData:()=>{
            //分发action 
            dispatch({type:'article/getData1',payload:{page:0,pageSize:10}});
        }
    }
}
export default connect(state => state, mapDispatchToProps)(Article);

article.js

//[src/services/article.js]
//article的service
import axios from '../utils/axios';
export const findArticle = (params)=>{
    return axios.get('/manager/article/findArticle',{params});
}

axios.js

//[src/utils/axios.js]
import config from './config';
//axios的配置
import axios from 'axios';
import qs from 'qs';
axios.defaults.baseURL = config.baseURL;
//拦截器 响应回来后拦截处理
axios.interceptors.response.use((response)=>{
    // console.log(response);
    //封装返回的数据
    //response.data是服务器返回的数据
    let res = {
        ...response,
        data: response.data.data,
        status: response.data.status,
        statusText: response.data.message
    };
    return res;
},(error)=>{
    //响应失败后拦截
    return Promise.reject(error);
});

//post请求发送前拦截
axios.interceptors.request.use((config) => {
    //config.data是json格式的数据,再使用qs转成表单格式数据
    //请求发送前拦截处理
    // console.log(config);
    if (config.method === 'post')   {
        config.data = qs.stringify(config.data);
    }
    return config;
},(error)=>{
    //请求发送失败处理
    return Promise.reject(error);
});

export default axios;

config.js

//[src/utils/config.js]
const baseURL = 'http://134.175.154.93:8099';
export default {
	baseURL 
}

index.js

//[src/index.js]
import dva from 'dva';
import './index.css';
import router from './router';
//article数据模型
// import article from './models/article';
// 1. Initialize
const app = dva();

// 2. Plugins
// app.use({});

// 3. Model
// app.model(require('./models/example').default);
// app.model(article);

require('./models').default.forEach(key => {
  app.model(key.default);
});


// 4. Router
// app.router(require('./router').default);
app.router(router);

// 5. Start
app.start('#root');

router.js

//[src/router.js]
//页面组件
import React from 'react';
import { Router, Route, Switch } from 'dva/router';
import IndexPage from './routes/IndexPage';
import Article from './routes/Article';

function RouterConfig({ history }) {
  return (
    <Router history={history}>
      <Switch>
        <Route path="/" exact component={IndexPage} />
        <Route path="/article" exact component={Article} />
      </Switch>
    </Router>
  );
}

export default RouterConfig;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值