Fork me on GitHub

vuex之module的使用

一、module的作用

由于使用单一状态树,应用的所有状态会集中到一个比较大的对象。当应用变得非常复杂时,store 对象就有可能变得相当臃肿。

为了解决以上问题,Vuex 允许我们将 store 分割成模块(module)。每个模块拥有自己的 state、mutation、action、getter、甚至是嵌套子模块——从上至下进行同样方式的分割:

二、module的使用方法

1、配置

  • 项目结构

  • 在index.js文件中进行组装
import Vue from 'vue'
import Vuex from 'vuex'
import state from './state'
import mutations from './mutations'
import getters from './getters'
import actions from './actions'
import user from './modules/user'
import rights from './modules/right'
import roles from './modules/role'
import homes from './modules/home'


Vue.use(Vuex);

//组装模块并导出 store 的地方
export default new Vuex.Store({
  //根节点相关
  state,
  mutations,
  getters,
  actions,

  //模块相关
  modules: {
    user,
    rights,
    roles,
    homes,

  },

});
  • 在main.js的vue中进行注册store
import router from './router'
import store from './store/index'


var vm = new Vue({
  el: '#app',
  router,
  store,
  components: {App},
  template: '<App/>'
});

2、使用

  • 以module文件夹中的user.js为例,如果建立的只是给固定的组件User组件使用,在user.js文件中使用命名空间
export default {

  namespaced: true,//使用命名空间,这样只在局部使用

  state: {

  },

  mutations: {

  },

  getters: {

}

}
  • 在User组件中发送ajax请求,注意携带命名空间的名称,也就是index.js组装时使用的名字
  created() {
      this.getUsers()
    },

  methods:{

      getUsers() {
        //将token设置在请求头中提交,已经在拦截器中设置
        // this.$http.defaults.headers.common['Authorization'] = localStorage.getItem("token");
        this.$store.dispatch('user/getAllUserList', {_this: this, query: this.query})//this是Vue实例

      },

}
  • 在user.js文件中的action进行异步操作
//有命名空间提交方式,类似this.$store.dispatch("user/getAllUserList");
  actions: {
    //将Vue实例进行传递接收
    // getAllUserList(context, _this) {
    //   //局部状态通过 context.state 暴露出来,根节点状态则为 context.rootState:

    //加入分页
    getAllUserList(context, object) {
      //局部状态通过 context.state 暴露出来,根节点状态则为 context.rootState:

      //发送get请求获取API数据  crm/user?page=${context.state.page}&size=${context.state.size}&username=${object.query}
     object._this.$http.get(`crm/user?page=${context.state.page}&size=${context.state.size}`)
        .then((response) => {
          // handle success
          context.commit('GETALLUSER', response.data);
          object._this.$message.success("获取数据成功")
          object._this.page=1

        })
        .catch((error) => {
          // handle error
          console.log(error);
        })
        .finally(() => {
          // always executed
        });
      // const response = await this.$http.get('crm/user');
      // context.commit('GETALLUSER', response);


    },
}
  • 在user.js的mutations中进行state值得修改
mutations: {


    //action中提交该mutation
    GETALLUSER(state, data) {
      state.UserList = data.results; //将添加成功的数据添加到状态,用于页面更新
      state.Total = data.count

    },
}

当然,在此之前state是需要初始化的:

  state: {

    UserList: [],
    Total: null,
    size: 2,
    query: null,
    page: 1,
}
  • 在getters中对state数据根据需求进行过滤
  getters: {
    getUserList: state => {

      return state.UserList;

    }
}
  • 在User组件中通过computed方法获取getters
import {mapGetters} from 'vuex'

export default {
    name: "User",

  computed: {
      ...mapGetters({

        UserList: 'user/getUserList',
   
      }),
    }
}

这样就可以在html中直接使用UserList属性了。

三、action、mutation、getters的互相调用

1、actions中调用其它action

    async delUser(context, object) {
      //context包含的参数:commit,dispatch,getters,rootGetters,rootState,state
    ...
    ...  
        //删除后刷新页面
        context.dispatch("getAllUserList", object._this)

      }
    },

在action中通过context.dispatch方法进行调用

2、getters中调用其它gerter

getters:{

   getRolesList: state => {
      return state.RoleList;
    },

    //调用其它getter
    getRoleIdList: (state, getters) => {
      let RoleIdArray = [];
      getters.getRolesList.forEach(item => {
        RoleIdArray.push(item.id);
      });
      return RoleIdArray
    },
}    

getters中可以传入第二个参数就是getters,然后通过这样使用其它getter。当然getters也可以传入根节点状态和getters。

 getters: {
      // 在这个模块的 getter 中,`getters` 被局部化了
      // 你可以使用 getter 的第四个参数来调用 `rootGetters`
      someGetter (state, getters, rootState, rootGetters) {
       
      },
     
    },

3、组件中获取getters

(1)带上命名空间访问

 getters['user/getUserList']

(2)通过辅助函数访问(推荐)

  import {mapGetters} from 'vuex'

    computed: {

      ...mapGetters({
        UserList: 'user/getUserList',
        total: 'user/getTotal',
        DeptList: 'user/geDeptList',
        RoleList: 'user/getRolesList',
        RoleIdList: 'user/getRoleIdList',
        AllRoleList: 'user/getALLRolesList',
        AllRoleIdList: 'user/getAllRoleIdList',
        permissionDict: 'getPermission'
      }),

    }

4、组件中提交action

this.$store.dispatch('user/setRole', {
          _this: this,
          id: this.currentuser.id,
          rid_list: {roles: this.CheckedRolesIdList}
        })

如果是全局的就不需要加上局部命名空间user

 

posted @ 2019-09-04 23:13  iveBoy  阅读(9881)  评论(0编辑  收藏  举报
TOP