Vue version used: 3
We all have been there: our apps grow and so does their state, and that means usually more stress on "How am I going to manage state between more components?" or "How do I pass data more easily through the components?". In this article, we will go about learning how to work with Vuex in order to make state management simpler and quicker in Vue applications.
How is state management applied in VueJS?
First, state in VueJS is reactive, which means that when the application state is changed, those changes are automatically reflected in the DOM (Document Object Model). State management can be made using both the "data" property in the Vue component you are working on. This is known as "single state tree", which means that a component manages all the state, view and actions itself. But, when you begin to scale your Vue app and state becomes more difficult to manage, things might get more complicated, hence a state management library makes more sense and will help you massively.
Luckily, there is another approach which is by setting up a store using Vuex and using the state define in it throughout our components.
But... what exactly is a "store"?
A "store" is a JavaScript file defined inside a folder called "store" where we define the state, actions, mutations, getters and modules of our app. We will go through each one separately.
First, let's setup Vuex in your Vue project
In order to setup and use Vuex, you can either install it right when creating the project with vue create project-name
or by installing it later using the following scripts or commands:
CDN
<script src="/path/to/vue.js"></script>
<script src="/path/to/vuex.js"></script>
NPM
npm install vuex@next --save
Yarn
yarn add vuex@next --save
Now that you have Vuex installed, you are able to create a store
. But what is it actually? It is the place where you will configure all the state
and all the changes that are made based on the user's input or an API call, for example.
Basic structure of a Vuex store
First, create an export
for the store
:
export default new Vuex.Store({})
Then, fill in with the properties of the store
that you need for your project:
export default new Vuex.Store({
state: {},
mutations: {},
actions: {},
getters: {},
modules: {}
})
There are other approaches to create a store
, such as by creating a variable to store each property of the store and adding them altogether inside a store
export as follows:
const state = {
count: 0
}
export default new Vuex.Store({
state: state
})
Now, what do you add inside each property of the store
?
state
holds the main "state" of our app.
state: {
users: [,,,,]
}
mutations
acts as "events" triggered that change the state
, but only allow synchronous operations.
mutations: {
increment: (state) {
state.count++
}
actions
are similar to mutations
, but allow asynchronous operations such as API calls. These do not mutate the state
, but commit mutations
instead.
actions: {
increment (context) {
context.commit(‘increment’)
}
}
getters
are a sort of "computed" property of a store
, which allow you to filter a list of items and counting them, for example. They receive state
as their first argument and can receive getters
as a second argument.
// in the store
getters: {
users: state => state.users
}
// in the component
computed: {
users() {
return this.$store.getters.users
}
}
modules
are like "containers" with separate state management for different purposes in our project. Let's imagine you have:
- a
state
for products on an e-commerce website - a
state
for an API call to get the users from a database
You can easily manage both using modules:
const products = {
state: {
products: ['t-shirt', 'jacket', 'hat', 'jeans']
}
...
}
const users = {
state: {
users: []
},
actions: {
... API call
}
}
export default new Vuex.Store({
modules: {
products,
users
}
})
How to access the store in a component?
In order to access the store
in a component, you can make use of $store
or this.$store
and then access the properties defined in the store
.
<template>
<div>
{{ state.users }}
</div>
</template>
export default {
name: "MyComponent",
store,
data() {
return {
state: store.state
}
}
}
This will render the state
in the UI.
// "john", "carl", "kent", "joost"
Vuex documentation
You can read the official documentation of Vuex here:
State management alternatives in 2022
It is a good choice if you go for Vuex when managing state in your Vue apps, but nowadays there are other tools you can pick from, such as Pinia.
We will go through Pinia in a future article.
Can components still have local state? 🤔
Yes, components can still have the so called "single state tree", as long as it's state
is not accessed outside of that component, hence you don't need to use a store for every component's state
.
Thank you for reading!
I hope that this article helped you gain an understanding of how Vuex and state management work in their core, and that you can take these tools to your project in the way you need and that will help you scale more easily. See you in the next article!👋
Top comments (3)
the latest Vue JS, they recommended using Pinia, I think it's time to move Pinia instead vuex
That is true indeed! I am preparing an article on Pinia soon actually 🍍 It is supposed to be the “Vuex 5” and it is pretty good. If you get the hang of Vuex well, learning Pinia is pretty easy 🙂
okay, i'll be waiting for the next article ^_^