Vuex Legacy

Traditional state management for Vue 2 applications

📚 What is Vuex?

Vuex is the original state management pattern for Vue applications. It serves as a centralized store with strict rules for predictable state changes, primarily used in Vue 2 projects.


// Basic Vuex store
import { createStore } from 'vuex'

const store = createStore({
  state: { count: 0 },
  mutations: {
    increment(state) {
      state.count++
    }
  }
})
                                    

Core Vuex Concepts

🏪

State

Single source of truth

state: {
  user: null,
  items: []
}
🔄

Mutations

Synchronous state changes

mutations: {
  SET_USER(state, user) {
    state.user = user
  }
}

Actions

Async operations

actions: {
  async fetchUser({ commit }) {
    const user = await api.get()
    commit('SET_USER', user)
  }
}
🔍

Getters

Computed store values

getters: {
  isLoggedIn: state => 
    !!state.user
}

🔹 Creating a Vuex Store

Set up a complete Vuex store with all core concepts:

// store/index.js
import { createStore } from 'vuex'

export default createStore({
  state: {
    todos: [],
    filter: 'all'
  },
  
  getters: {
    filteredTodos: (state) => {
      if (state.filter === 'completed') {
        return state.todos.filter(t => t.completed)
      }
      return state.todos
    }
  },
  
  mutations: {
    ADD_TODO(state, todo) {
      state.todos.push(todo)
    },
    TOGGLE_TODO(state, id) {
      const todo = state.todos.find(t => t.id === id)
      if (todo) todo.completed = !todo.completed
    }
  },
  
  actions: {
    addTodo({ commit }, text) {
      commit('ADD_TODO', {
        id: Date.now(),
        text,
        completed: false
      })
    }
  }
})

🔹 Using Vuex in Components

Access store state and dispatch actions in components:

<template>
  <div>
    <h2>Todo Count: {{ todoCount }}</h2>
    <ul>
      <li v-for="todo in filteredTodos" :key="todo.id">
        {{ todo.text }}
      </li>
    </ul>
    <button @click="addNewTodo">Add Todo</button>
  </div>
</template>

<script>
import { mapState, mapGetters, mapActions } from 'vuex'

export default {
  computed: {
    ...mapState(['todos']),
    ...mapGetters(['filteredTodos']),
    todoCount() {
      return this.$store.state.todos.length
    }
  },
  methods: {
    ...mapActions(['addTodo']),
    addNewTodo() {
      this.addTodo('New task')
    }
  }
}
</script>

🔹 Modules for Organization

Split large stores into separate modules:

// store/modules/user.js
export default {
  namespaced: true,
  state: { profile: null },
  mutations: {
    SET_PROFILE(state, profile) {
      state.profile = profile
    }
  },
  actions: {
    updateProfile({ commit }, profile) {
      commit('SET_PROFILE', profile)
    }
  }
}

// store/index.js
import user from './modules/user'

export default createStore({
  modules: {
    user
  }
})

// Usage in component
this.$store.dispatch('user/updateProfile', data)

🔹 Vuex vs Pinia

Understanding the differences:

Why Pinia is Recommended:

  • Simpler API: No mutations, just actions
  • TypeScript: Better type inference
  • Modular: Each store is independent
  • DevTools: Enhanced debugging experience
  • Vue 3: Designed for Composition API

Note: Vuex is in maintenance mode. Use Pinia for new projects.

🔹 Installation & Setup

Set up Vuex in your Vue application:

// Install: npm install vuex@next

// main.js
import { createApp } from 'vue'
import store from './store'
import App from './App.vue'

const app = createApp(App)
app.use(store)
app.mount('#app')

🧠 Test Your Knowledge

Which Vuex concept handles asynchronous operations?