簡體   English   中英

如何在不異步承諾的情況下編寫Vuex變異

[英]How to write Vuex mutation without asynchronous promise

我正在使用Vue.js,Vuex和Firebase構建應用程序。 在此應用中,Firestore數據庫中的數據會更新為突變狀態。 當前狀態的應用程序似乎可以正常運行,因為然后通過getters方法將狀態返回到模板。 但是,據我了解,突變是同步的,promise(.then)是異步的。 因此,.then承諾不應包含在突變內部。 那么,為什么這個應用程序仍然可以正常執行? 重新配置突變以使FB數據無須更新到狀態的最佳方法是什么? 還是有必要改變這一點? 這是我的Vuex代碼。 謝謝!

import Vue from 'vue'
import Vuex from 'vuex'
import firebase from 'firebase'
import db from '@/firebase/init'

Vue.use(Vuex)

export default new Vuex.Store({
  state: {
    items: null
  },
  getters: {
    getItems: state => {
      return state.items
    }
  },
  mutations: {
    setAllUser: state => {
      const items = []
      db.collection('users').get()
      .then(snapshot => {
        snapshot.forEach(doc => {
          let userData = doc.data()
          userData.id = doc.id
          items.push(userData)
        })
        state.items = items
      })
    },
  actions: {
    setAllUser: context => {
      context.commit('setAllUser')
    }
  }
})


**SOLUTION**

import Vue from 'vue'
import Vuex from 'vuex'
import firebase from 'firebase';
import db from '@/firebase/init'

Vue.use(Vuex)

export default new Vuex.Store({
  state: {
    items: null
  },
  getters: {
    getItems: state => {
      return state.items
    }
  },
  mutations: {
    setAllUser: (state, items) => {
      state.items = items
    }
  },
  actions: {
    setAllUser: async context => {
      let snapshot = await db.collection('users').get();
      const items =[]
      snapshot.forEach(doc => {
        let userData = doc.data()
        userData.id = doc.id
        items.push(userData)
      })
      context.commit('setAllUser', items)
    }
  }
})

將您的異步代碼移至動作:

{
  mutations: {
    setAllUser: (state, items) => state.items = items
  },
  actions: {
    setAllUser: async context => {
      let snapshot = await db.collection('users').get();
      let items = snapshot.map(doc => {
        let userData = doc.data();
        userData.id = doc.id
        return userData;
      });
      context.commit('setAllUser', items)
    }
}

那么為什么呢?

  • 單一責任:您的突變只應負責設定狀態。
  • 不知道vue-devtools會如何反應,我想它只會顯示一個突變。
  • 您的突變應僅取決於有效負載和狀態,而不取決於網絡/服務器響應等
  • 您的同事不會期望這種情況發生

為什么有效?

  • 如果您直接從devtools直接執行此操作,則會出現相同的原因: window.store.state.items = [] Vuex只會覆蓋getters並更新狀態,從而更新dom。

附注:您可以在操作中使用promise.then而不是await

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM