How to make a form handling with vuex
Matheus Gomes 👨💻
Posted on December 30, 2019
Problem
Let's say you want to save the input of your form on the state of vuex.
Maybe someone new to vuex would try something like this:
<input id="name" name="name" type="text" v-model="$store.state.user.name">
If you try this you will see that:
- It doesn't work
- Even if it worked, it is totally against the purpose of vuex, that is never have a change of state without it being made by a mutation.
Always send a mutation to change something.
Now, with that in mind, if you look into the documentation of vuex you will find the following:
[...] An alternative approach is using a two-way computed property with a setter:
<input v-model="message">
// ...
computed: {
message: {
get () {
return this.$store.state.obj.message
},
set (value) {
this.$store.commit('updateMessage', value)
}
}
}
You can use the v-model to change, but you will need to register a computed property with a getter and a setter to change the state.
Works?
Works.
But let's say you have a form, you will need to make a getter and a setter to every input. This works, but isn't practical.
The best way to do it, in my opinion, is to use the principles of clean code to make it:
export function mapFields(options) {
const object = {};
for (let x = 0; x < options.fields.length; x++) {
const field = [options.fields[x]];
object[field] = {
get() {
return this.$store.state[options.base][field];
},
set(value) {
this.$store.commit(options.mutation, { [field]: value });
}
};
}
return object;
}
Where mapField is the function that map all the field and handle the form. Options is an object with a field which is the field you want to map and a base to refer.
At the end it will only return the getter and setter to us, not so different from before, but with a lot less code.
EDIT: I forgot to show how to use it, so here it is.
I would put it on some helper.js, so i can just import it from my userForm.vue, like this:
<script>
import { mapFields } from "@/helpers.js"
export default {
computed: {
...mapFields({
fields: ["name", "email", "street", "zipcode"],
base: "user",
mutation: "UPDATE_USER"
}),
...
Hope you enjoyed my first post here, any questions comment bellow! 😎
Happy new year
Posted on December 30, 2019
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.