vuex的模块化

vuex 深层学习modules



前言

首先,回顾一下vuex的核心概念(个人理解,方便记忆理解):

  1. state: 共享的数据
  2. mutations:同步操作,修改state数据的唯一方法 第一个形参是state数据 第二个形参是外面传入的数据
  3. actions:存储修改,异步操作 第一个参数表示上下文对象,第二个表示外部传入的数据
  4. getters:类似于计算属性,不允许修改 ,对state数据进行包装加工处理
  5. modules:模块化(也就是今天学习的内容)

提示:以下是本篇文章正文内容,下面案例可供参考

一、modules是什么?

  1. 官方介绍:modules,可以让每一个模块拥有自己的state、mutation、action、getters,使得结构非常清晰,方便管理;如果所有的状态或者方法都写在一个store里面,将会变得非常臃肿,难以维护。
  2. 个人理解:为了让状态管理变得清晰,容易维护,适用于比较复杂的大型项目。可以拥有属于自己的state、mutation、action、getters、modules 互不影响。
  3. 这个图很重要 一定要记住哟!!!
    在这里插入图片描述

二、如何实现模块化

1.创建

modules里面的state可以是函数,可以拥有这些自己的state、mutation、action、getters、modules

export default new Vuex.Store({
    
    
  state: {
    
    },
  getters:{
    
    },
  mutations: {
    
    },
  actions: {
    
    },
  modules: {
    
    
  	模块名1:{
    
    
            state:()=>({
    
    }),
            getters:{
    
    },
            mutations:{
    
    },
            actions:{
    
    },
            modules:{
    
    }
    },
    模块名2:{
    
    
            state:()=>({
    
    }),
            getters:{
    
    },
            mutations:{
    
    },
            actions:{
    
    },
            modules:{
    
    }
     }
  }
})

这样写全部都在store/index.js里面难以维护,所以进行文件的抽离

模块1.js

export default ({
    
    
  	state: {
    
    },
  	getters:{
    
    },
 	mutations: {
    
    },
  	actions: {
    
    },
 	modules:{
    
    }
  }
})
index.js 中导入模块

import 模块1 from './modules/模块1';
import 模块2 from './modules/模块2';

export default new Vuex.Store({
    
    
  state: {
    
    },
  getters:{
    
    },
  mutations: {
    
    },
  actions: {
    
    },
  modules: {
    
    
  	模块名1,
    模块名2
  }
})

2. 获取模块数据 调用模块方法

2.1 模块state
方法1:{
    
    {
    
     $store.state.模块名.属性名 }}
方法2:import {
    
     mapState } from 'vuex';
	  computed:{
    
    
    		// 注意:对象写法
    		...mapState({
    
    
        		属性名:state=>state.模块名.属性名
   			}) 
	   }
2.2 模块getters
方法1:{
    
    {
    
     $store.getters.属性名 }}
方法2:import {
    
     mapGetters } from 'vuex'    
	  computed:{
    
    
     	...mapGetters(['属性名']) 
	  } 
2.3 模块mutations
方法1:$store.commit('方法名',实参)
方法2:import {
    
     mapMutations } from 'vuex'
	  methods:{
    
    
		...mapMutations(['方法名'])
	  }
2.4 模块actions
方法1:$store.dispatch('方法名',实参)
方法2:import {
    
     mapActions} from 'vuex'
	  methods:{
    
    
		...mapActions(['方法名'])
	  }

学到这,大家有没有发现,除了state模块有区别,其他的获取和出发没什么区别,那么问题来了,如果模块化下的属性名和方法名,与根模块下的重复则会出现问题报错之类的,所以我们使用 命名空间来实现具体的模块化操作

3.开启命名空间(namespaced)

export default ({
    
    
  	state: {
    
    },
  	getters:{
    
    },
  	mutations: {
    
    },
  	actions: {
    
    },
  	modules:{
    
    },
  	namespaced:true // 默认为false
  }
})

在获取模块数据 调用模块方法的时候 一定要注意是哪个模块下面的属性名称

3.1 命名空间下的state
方法1:{
    
    {
    
     $store.state.模块名.属性名 }}
方法2:import {
    
     mapState } from 'vuex';
	  computed:{
    
    
    		// 注意:对象写法
    		...mapState({
    
    
        		属性名:state=>state.模块名.属性名
   			}) 
	   }
3.2 命名空间下的getters
方法1:{
    
    {
    
     $store.getters['模块名/属性名'] }}
方法2:import {
    
     mapGetters } from 'vuex'    
	  computed:{
    
    
     	...mapGetters({
    
    
     		属性名:'模块名/属性名'
     	}) 
	  } 
3.3 命名空间下的mutations
方法1:$store.commit('模块名/方法名',实参)
方法2:import {
    
     mapMutations } from 'vuex'
	  methods:{
    
    
		...mapMutations({
    
    
			方法名:'模块名/方法名'
		})
	  }
3.4 命名空间下的actions
方法1:$store.dispatch('模块名/方法名',实参)
方法2:import {
    
     mapActions} from 'vuex'
	  methods:{
    
    
		...mapActions({
    
    
        	模块名/方法名:'模块名/方法名'
        })
	  }

三、遇到的问题分享

学到这,有没有觉得 这样记忆很麻烦 又有 单页面的状态管理的写法 又有多页面的写法 又分开启命名空间的,这样记忆确实很麻烦 所以我们可以 利用根模块的getters包装子模块的state数据, 可以用 根模块的actions里面访问其他模块的actions或者mutations

// 将子模块的state,变成根模块下的getters
export default new Vuex.Store({
    
    
	getters:{
    
    
        namelist:function(state){
    
    
            // state 表示所有的state数据,包括子模块下的
            return state.role.rolelist
        },
        // 简写
        //namelist:state=>state.role.rolelist
    }
})

//子模块写法
{
    
    
	state:()=>({
    
    
		namelist:[]
	}),
	namespaced:true
}
// 子模块的actions调用其他模块的actions或者mutations
actions:{
    
    
	方法名(context){
    
    
		context.commit('方法名')  // 触发自己的mutations方法
        context.commit('模块名/方法名') // 触发自己的子模块的mutations方法
        context.commit('方法名',null,{
    
    root:true}) // 触发根模块的mutations方法或者没开启命名空间模块下的mutations方法
        context.commit('模块名/方法名',null,{
    
    root:true})  // 触发其他模块的mutations方法
   
        context.dispatch('方法名')  // 触发自己的actions方法
        context.dispatch('模块名/方法名') // 触发自己的子模块的actions方法
        context.dispatch('方法名',null,{
    
    root:true}) // 触发根模块的actions方法或者没开启命名空间模块下的actions方法
        context.dispatch('模块名/方法名',null,{
    
    root:true})  // 触发其他模块的actions方法
	}
},
namespaced:true  // 开启了命名空间

总结

好了,今天就学习到这,希望今天的学习能对你有所帮助,记得多多支持哟!

往期文章:
uniapp 图片预览实现
vuex学习篇

猜你喜欢

转载自blog.csdn.net/m0_56144469/article/details/126682356