Vuex命名空间及如何获取根模块、兄弟模块状态管理器

模块化思想

import global from './modules/global';
import form from './modules/form';
import formDesign from './modules/form-design';
...

const store = new Vuex.Store({
  state: {},
  mutations: {},
  actions: {},
  strict: true,
  modules: {
    global,
    form,
    formDesign,
    ...
  },
  ...
}

 

 此时这个项目结构就很简单清晰啦 ,我们来看看模块的状态管理器长啥样

        其实就是和状态管理器一样,有state有mutations ,甚至你喜欢的话,还可以往里面继续嵌套模块module。形成三级、四级、五级等等多层级的模块化状态管理器。

命名空间

        上面看到,我们把主状态管理器分割为多个模块。默认情况下,模块内部的 action、mutation 和 getter 是注册在全局命名空间的,这样使得多个模块能够对同一 mutation 或 action作出响应。所以我们需要单独的命名空间保证模块化管理的封装度和复用性。

        首先我们需要在单个模块中通过添加namespaced:true的方式使其成为带命名空间的模块,也就是刚才我们看到的:

const file = {
  namespaced: true,
  state: {
      fileName:'小文件',
      ...
  },
  mutations: {
    ...
  },
  actions: {
    ...
  },
};

export default file;

 此时在组件内部,获取state的方法

this.$store.state.file.fileName

 此时在组件内部,获取getters的方法

this.$store.getters['file/fileGetter']

  此时在组件内部,执行Mutations的方法

 this.$store.commit('file/fileMutation');

此时在组件内部,执行Actions的方法

this.$store.dispatch('file/fileAction')

带命名空间的moduleA,moduleB模块中,获取根store的state ,getters

   state数据: 通过rootState参数    即:rootState.属性名

          getter方法:通过rootGetters参数来获取   即:rootGetters.countStudentNumber

{
...
actions: {
    async init({state,rootState,rootGetters}) {
         return rootGetters.countStudentNumber
    },
}
}

        如果要传承,可以这样写:

// 主store下的
getters: {
    applicationAdminPermission: (state) => (appId) =>
      state.applicationAdminList.includes(appId),
}

        主store的getters里的函数接收state内参和appid外参。子模块moduleA调用这个getters方法并传参:

{
...
actions: {
    async checkIt({state,rootState,rootGetters}) {
        const checkResult = rootGetters.applicationAdminPermission('usyddjj16236')
    },
}
}

        如果你想传多个参数,只能以对象的形式传参

// 主store下的
getters: {
    applicationAdminPermission: (state) => (appObj) =>
      state.applicationAdminList.includes(appObj.appId),
}
{
...
actions: {
    async checkIt({state,rootState,rootGetters}) {
        const checkResult = rootGetters.applicationAdminPermission({appName:'大傻逼',appId:'usyddjj16236'})
    },
}
}

带命名空间的moduleA,moduleB模块中,获取根store的actions和mutations

         提交mutations:

actions: {
    changeTenant() {
        //increment为根store中的mutation
        commit('increment',null,{root:true});    
    }
}

        分发actions:

actions: {
    changeTenant() {
        //increment为根store中的actions
        dispatch('increment',{tenant:'xxx'},{root:true});    
    }
}

           其实就是加上{root:true}这个option。而主Vuex下的actions和mutations并不需要特殊处理。

带命名空间的moduleA,moduleB模块中,获取兄弟模块的state和getters

        moduleA:

const moduleA = {
    namespaced: true,
    state: {
        title:'我叫moduleA'
    },
    getters: {    
        customTitle(state){
            return '你好' + state.title
        }
    }
};

export default moduleA;

        moduleB获取moduleA的state和getters

const moduleB = {
    namespaced: true,
    state: {
        title:'我叫moduleB'
    },
    actions: {
        getModuleAstate({
            state,
            commit,
            dispatch,
            rootState,
        }){
            
            console.log(rootState.moduleA.title)

        },
        getModuleAGetters({rootGetters}) {
            console.log(rootGetters['moduleA/customTitle'])
        }
    }
};

export default moduleB;

带命名空间的moduleA,moduleB模块中,获取兄弟模块的actions和mutations

        moduleA:

const moduleA= {
    namespaced: true,
    state: {},
    mutations: {
        Aaaa(state,{val}){
            console.log(val)
        },
    },
   actions: {
        Abbb({state},{val}){
            console.log(val)
        },
    }
};

export default moduleA;

        moduleB:

const ceshi2 = {
    namespaced: true,
    state: {
       
    },
    mutations: {
       
    },
    actions: {
        hanleChange({
            rootState,
        }){
            commit('moduleA/Aaaa',{val:'你好我的朋友'},{root:true})
            dispatch('moduleA/Abbb',{val:'你好我的宝贝'},{root:true})
        },
    }
};

在带命名空间的模块中,如何将action注册为全局actions

            需要完成:

           ①添加 root: true
           ②并将这个 action 的定义放在函数 handler 中


//storeAction在命名空间moduleA中,但是它是一个全局actions
const moduleA = {
    namespaced:true,
    storeAction:{
        root:true,  //条件1
        handler(namespacedContext, payload){//条件2:handler
            //namespacedContext 上下文信息
            //payload 载荷,即参数
            console.log(namespacedContext)
            console.log(payload)
            alert("我是模块A中的全局storeAction")
        }
    }
}

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值