I've managed to break VueJS reactivity with my Vuex store thanks (I think) to a complex data model. The data is an object of arrays of objects as follows:
"users": {
"2017": [
{ id: 1, name: "bob" },
{ id: 2, name: "jane" },
],
"2016": [
...
]
},
"dude": null
I had originally been storing ES6 classes in the store (I have a lot of helper functions) but have since removed that.
In order to access the right user I have a computed property as follows:
computed: {
user () {
return this.$store.state.users.users[this.$store.state.users.currentDate][this.$store.state.users.currentUserIndex]
},
...
The problem occurs when I commit a mutation to update the name (for example), I can see in the Chrome Vue debugger that the state has changed however the template has not (i.e. user.name
continues to be the previous name).
Here is the code for the mutation:
PATCH_USER (state, payload) {
let index = state.users[state.currentDate].findIndex((el) => el.id === payload.user.id)
let user = Object.assign(state.users[state.currentDate][index], payload.user)
Vue.set(state.users[state.currentDate], index, user)
},
Now, that part that makes me thing I'm doing something silly. If I add a computed property for dude
(root level state item) and then include it in the template then the user name is correctly updated.
There is a lot more to the application but hopefully I'm doing something wrong with what I've shown.
Any help is much appreciated!
UPDATE
Figures after 8 hours of wrestling with this the answer seems to have come within 2 mins of posting to SO. (thanks @blockhead and @bert-evans).
I thought I had checked all of the code for this however it turns out the very first time data was loaded from the backend server it was wrong. payload
is the response from the web API:
// bad
SET_USERS (state, payload) {
state.users[state.currentDate] = payload.users
}
// good
SET_USERS (state, payload) {
Vue.set(state.users, state.currentDate, payload.users)
}