Vue and Vuex


The workflow of store workflow

Good example

Basic Concepts

Store is the center of vuex. Store is where vuex saves all data together. Store will hold the application State.
When Vue components retrieve state from it, they will reactively and efficiently update if the store’s state changes.

const store = new Vuex.Store({
  state: {
    count: 0
  mutations: {
    increment (state) {

You cannot directly mutate the store’s state. The only way to change a store’s state is by explicitly committing mutations.

If we want to execute the increment function,


Vuex uses a single state tree which contains all your application level state and serves as the “single source of truth”.

This also means usually you will have only one store for each application

For the best practice, we can create a store folder.


Within the store/index.js, we set:


Then use it in main.js

new Vue({

By providing the store option to the root instance, the store will be injected into all child components of the root and will be available on them as this.$store

For Example:

const Counter = {
  template: `<div>{{ count }}</div>`,
  computed: {
    count () {
      return this.$store.state.count


mapState is a helper for vuex. When using the state within the component, it will be insufficient to declare getter function one by one. We can use mapState to simply map one this attribute to state.


// in full builds helpers are exposed as Vuex.mapState
import { mapState } from 'vuex'

export default {
  // ...
  computed: mapState({
    // arrow functions can make the code very succinct!
    count: state => state.count,

    // passing the string value 'count' is same as `state => state.count`
    countAlias: 'count',

    // to access local state with `this`, a normal function must be used
    countPlusLocalState (state) {
      return state.count + this.localCount

Object Spread Operator

it’s kind of advanced function for mapState e.g.

computed: {
  localComputed () { /* ... */ },
  // mix this into the outer object with the object spread operator
    // ...


getters is a list of function defined in Store which can be reused in multiple component.


mapGetters is similar to mapState. It reduce the complexity of importing getters function.

Commit with Payload

mutations: {
  increment (state, payload) {
    state.count += payload.amount
store.commit('increment', {
  amount: 10

Using Constants for Mutation Types

The best practice is to define mutation types within the project.

// mutation-types.js
// store.js
import Vuex from 'vuex'
import { SOME_MUTATION } from './mutation-types'

const store = new Vuex.Store({
  state: { ... },
  mutations: {
    // we can use the ES2015 computed property name feature
    // to use a constant as the function name
    [SOME_MUTATION] (state) {
      // mutate state

Mutations Must Be Synchronous

But we can use async/await within the mutation functions


mapMutations is a better way to import mutation functions

import { mapMutations } from 'vuex'

export default {
  // ...
  methods: {
      'increment', // map this.increment() to this.$store.commit('increment')

      // mapMutations also supports payloads:
      'incrementBy' // this.incrementBy(amount) maps to this.$store.commit('incrementBy', amount)
      add: 'increment' // map this.add() to this.$store.commit('increment')


Due to using a single state tree, all state of our application is contained inside one big object. However, as our application grows in scale, the store can get really bloated.

To help with that, Vuex allows us to divide our store into modules. Each module can contain its own state, mutations, actions, getters, and even nested modules – it’s fractal all the way down:

const moduleA = {
  state: { ... },
  mutations: { ... },
  actions: { ... },
  getters: { ... }

const moduleB = {
  state: { ... },
  mutations: { ... },
  actions: { ... }

const store = new Vuex.Store({
  modules: {
    a: moduleA,
    b: moduleB

store.state.a // -> moduleA's state
store.state.b // -> moduleB's state


Asynchronous logic should be encapsulated in, and can be composed with actions.

├── index.html
├── main.js
├── api
│   └── ... # abstractions for making API requests
├── components
│   ├── App.vue
│   └── ...
└── store
    ├── index.js          # where we assemble modules and export the store
    ├── actions.js        # root actions
    ├── mutations.js      # root mutations
    └── modules
        ├── cart.js       # cart module
        └── products.js   # products module

CSS Grid

CSS grid is a layput solution.