vuex是一套相對獨立的代碼,因此可以抽象出到單獨的文件夾裏,那麼比較好的代碼結構是啥樣的?
話不多說,以下是vuex比較好的代碼結構
├── index.html
├── main.js
├── api
│ └── ... # 抽取出API請求
├── components
│ ├── App.vue
│ └── ...
└── store
├── index.js # 我們組裝模塊並導出 store 的地方
├── getter.js # 根級別的 getter
├── actions.js # 根級別的 action
├── mutations.js # 根級別的 mutation
├── mutation-type.js # 將mutation名常量集中
└── modules
└── myModule.js # 單獨模塊
由此可以看出vuex的每個功能模塊爲一個單獨的js文件
下面分別說明每個js文件內容
1.index.js
index.js主要是導出vuex的,以及將全局的state聲明在其中,示例代碼如下
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
import actions from './actions'
import getters from './getters'
import mutations from './mutations'
import stock from './module/stock'
let state = {
user_info: //用戶信息
JSON.parse(localStorage.getItem('user_info')),
address_list: //用戶常用地址
JSON.parse(localStorage.getItem('address_list'))
}
export default new Vuex.Store({
state,
actions,
getters,
mutations,
modules:{
stock
},
})
以上可以看出,所有模塊均在index中引入,state內聲明瞭兩個狀態,以及將new 的vuex導出,這樣便可以在main.js內引入了
爲什麼狀態從localStorage中取值?
假如初始值user_info = ‘’;在某個時間單純給user_info賦值,如果不刷新頁面這個值會一直存在,那麼當你點擊刷新按鈕刷新當前頁面時,user_info就回到初始值空值了,爲什麼?因爲vuex中的狀態值時放在內存當中的,當你刷新頁面時這些值被釋放掉了,就找不到了,因此存在本地(方法之一)即使刷新也不會導致狀態丟失
2.mutations.js
import {SET_ADDRESS,UPDATE_USERINFO} from './mutation-types'
export default {
//更新倉庫地址
[UPDATE_ADDRESS] (state, newVal){
state.address_list = newVal;
localStorage.setItem('address_list',JSON.stringify(newVal));
},
//更新倉庫用戶信息
[UPDATE_USERINFO] (state, newVal) {
state.user_info = newVal;
localStorage.setItem('user_info',JSON.stringify(newVal));
},
}
這裏的是若干的函數,用來提交倉庫的更新,因爲不能直接對倉庫狀態更新,函數名統一聲明在mutation-type.js內
export const UPDATE_ADDRESS = "UPDATE_ADDRESS";
export const UPDATE_USERINFO = "UPDATE_USERINFO";
//------------------------------------------------myModule------------------------------------//
export const MY_MODULE_FUNC = "MY_MODULE_FUNC";
爲什麼要單獨聲明呢,首先官方建議是這麼做的,其次這樣也的確適合大型項目的統一管理,好處在你達到一定規模自然會體現出來
3.getters.js
export default{
user_name(state) {
return state.user_info.user_name + 'Hello!';
}
}
getters.js主要是篩選倉庫狀態的封裝,相當於一個組件內的computed,對倉庫內的狀態進一步加工
4.actions.js
export default {
updateUserInfo ({commit, newVal}) {
axios('http://xxxxx',{
user_info: newVal
}).then((res) => {
commit("SET_SHOPLIST",data.data.shop_list);
}).catch((err) => {
console.log(err);
})
}
}
actions.js主要是進行一些異步操作,以及對mutation的提交更新,由於在mutation內不能進行異步操作(官方建議最好是不要),因此有了actions
5.module(myModule.js)
模塊就是相對單獨的一個vuex,內部有單獨享有的狀態state,mutations等等
import {MY_MODULE_FUNC} from './../mutation-types'
export default {
namespaced: true,
state: {
count: 0
},
mutations: {
[MY_MODULE_FUNC] (state,newVal) {
state.count = newVal;
}
}
}
6.在main.js內引入到全局
import Vue from 'vue'
import App from './App'
import router from './router'
import store from './store'
Vue.config.productionTip = false
new Vue({
el: '#app',
router,
store,
components: { App },
template: '<App/>'
})
7.在組件中使用vuex
vuex的文件目錄以及十分清晰了,那麼如何使用這些呢,一下在組件中使用的方式
<template>
<span>Hello World!</span>
</template>
<script>
import {mapState,mapMutations,mapGetters,mapActions} from 'vuex'
export default {
name: 'Hello',
props: ['name'],
mounted() {
console.log(this.count);
console.log(this.user_info);
let address = [{add1: 'xxx', add2: 'xxx'}];
this.UPDATE_ADDRESS(address);
},
computed: {
//模塊內的獨立倉庫
...mapState('myModule',[
"count"
]),
// 公共區域的倉庫
...mapState([
'user_info',
'address_list'
]),
// getter
...mapGetters([
'user_name'
])
},
methods: {
// 模塊內的獨立mutations
...mapMutations('myModule',[
'MY_MODULE_FUNC'
]),
...mapMutations([
'UPDATE_ADDRESS',
'UPDATE_USERINFO'
])
//異步操作提交mutation的action
...mapActions([
'updateUserInfo'
])
}
}
</script>
其實引入方式有很多種,官網都有介紹,但是通過通過vuex的各個分發函數以及ES6的展開運算符能夠更加簡便的使用,分發在組件中之後就如同在組件中聲明的變量及函數,可以通過當前對象this訪問到,但是要注意一點,在computed中已經映射的狀態,不能再在data裏重複聲明同名變量,函數類似
OK,以上是完整的vuex項目結構及引用