dva在hooks中的简单使用(immer)

1 篇文章 0 订阅
1 篇文章 0 订阅

配置

在umi文件夹下有一个.umirc.ts文件,在文件中写入
dva: { immer: true, },
就开启了dva的immer模式
注:如需兼容 IE11,需配置 { immer: { enableES5: true }}。

约定式model的创建

符合以下规则的文件会被认为是 model 文件,
src/models 下的文件
src/pages 下,子目录中 models 目录下的文件
src/pages 下,所有 model.ts 文件

+ src
  + models/a.ts
  + pages
    + foo/models/b.ts
    + bar/model.ts

其中 a.ts,b.ts 和 model.ts 如果其内容是有效 dva model 写法,则会被认为是 model 文件。

model模板

import { Effect, ImmerReducer } from 'umi';
//api为封装的请求
import api from '@/https/api'
//定义类型的接口,ts可用
export interface IndexModelState {
  name: string;
  baseUrl: string;
}

export interface IndexModelType {
  namespace: 'index';
  state: IndexModelState;
  effects: {
    login: Effect;
  };
  reducers: {
    // 启用 immer 之后
    save: ImmerReducer<IndexModelState>;
  };
}

//实际数据及方法使用
const IndexModel: IndexModelType = {
//namespace是唯一标识,用于快速找到对应的model
  namespace: 'index',
 //类似vue中的state,用于管理状态,存储共享数据 
  state: {
    name: 'lili',
    baseUrl: 'http://localhost:7001'
  },
//类似于vuex的action,一般用于管理请求,并将请求结果由下方的reducers来改变state中数据值
  effects: {
  //方法,一般用来发请求,有两个参数,第一个为传递过来的参数,第二参数对应操作
    *login({playLoad}, { call, put }) {
      try {
        const res = yield call(api.login, { username: 111, password: 222 })
        console.log(res)
        yield put({ type: 'save', payLoad: { name: '456' } })
      } catch (err){
          console.log(err)
      }
    },
//类似vuex mutations
  reducers: {
    // 启用 immer 之后
    save(state, action) {
      console.log(action.payLoad.name)
      state.baseUrl = action.payLoad.name;
    },
  },
};
export default IndexModel;

下方有effect中参数详细

组件中实际使用

在组件导入中将useSelector, useDispatch 导入

import React, { useState, useEffect } from 'react'
import {useSelector, useDispatch } from 'umi';

const index = () => {
const dispatch = useDispatch()
//与redux使用方法相似,store为所有的model模块,详细见下图
let name=useSelector(store=>store.index.name)
let change = ()=>{
       dispatch({
       //page是model的唯一namespace,save是其reducers中方法
           type: 'page/save',
           //login是effects中方法
           //type: 'page/login',
           //payLoad用来传递参数,在model中effect的{playLode}和reducers的action中接收
           payLoad: {
                name: '柠檬啊'
            }
       })
}
    return (
        <div>
            <button onClick={change}>改变state中的值</button>
        </div>
    )
}
export default index

store内容在这里插入图片描述

model中使用其他effect方法以及reducers中方法

  *login({palyLoad}, { call, put }) {
      try {
      //api.login为封装的promise请求,palyLoad为请求所需参数
        const res = yield call(api.login, palyLoad)
        console.log(res)
       // 请求成功后,就可以将对应的请求data,通过reducers中方法提交到state中,其中put类似于dispatch
        yield put({ type: 'save', payLoad: { name: '456' } })
      } catch (err){
          console.log(err)
      }
    },

以这个方法为例,{playLoad}为dispatch提交上来的参数
用res来接收call发出请求的返回值
在这里插入图片描述

部分文字来源umi官网 https://umijs.org/zh-CN/plugins/plugin-dva

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值