burtonLowel
burtonLowel

Reputation: 794

Vue: Is it possible to set another state inside a Vuex action?

I have a Vuex action called activateProgram that I dispatch. I would like a state set inside of there called loadingData to be set to true and then set it to false when the api request is finished. I'd like to use this state as a flag for a spinner on my view. Is this possible?

actions: {
    activateProgram: (context, data) => {
        /// SET A ANOTHER STATE RIGHT HERE TO MARK THAT A REQUEST STARTED
        return axios.post(data.url, data.request)
            .then((response) =>
                 /// SET THAT STATE TO FALSE WHEN THE API REQUEST IS FINISHED
                context.commit('toggleProgram', true)
            )
            .catch((error) =>
                context.commit('toggleProgram', false)
            );
    }
 }

Upvotes: 0

Views: 394

Answers (1)

rossta
rossta

Reputation: 11494

The following is a fairly common pattern, borrowed from this post:

const actions = {
  fetchApiData (store) {  
    // sets `state.loading` to true. Show a spinner or something.
    store.commit('API_DATA_PENDING') 

    return axios.get('someExternalService')
      .then(response => {       
        // sets `state.loading` to false 
        // also sets `state.apiData to response`
        store.commit('API_DATA_SUCCESS', response.data) 
      })
      .catch(error => { 
        // set `state.loading` to false and do something with error   

        store.commit('API_DATA_FAILURE', error)
      })
    }
}

Add a loading flag to your state. It may make sense to group loading and toggleProgram mutations together. The "pending" mutation could toggle the loading to true, while the "success" and "failure" commits would set loading to false and mutate the program state as desired.

Doing this for every ajax post could get tiresome, so a next step could be to add an abstraction.

Upvotes: 3

Related Questions