Skip to content
Advertisement

Data object defined in created function but NOT reactive?

I have a Vue instance where data property is initialised as an object:

var app = new Vue({
  el: '#app',
  data: {
    obj: { }
  },
  methods: {

  },
  created: function() {
    this.obj["obj2"] = {}
    this.obj["obj2"].count = 0
  },
  mounted: function() {
    setInterval(function() {
      this.obj.obj2.count++
      console.log(this.obj.obj2.count)
    }.bind(this), 1000)
  }
})
<div id="app">
  {{ obj['obj2'].count }}
</div>

And then when the instance is created I add a property to the obj.

However, when I want to display the object’s object property count, it shows 0 and is not reactive. If I defined the whole object in the data, it is reactive but I can’t define the object in the data because its data depends on an external source – API, that’s why it is filled with data in created function.

The only way how I managed to make it show the current count is by forcing updates on the view but I don’t think it’s the correct solution.

Any suggestions?

enter image description here

Advertisement

Answer

The problem is that Vue can not track completely new properties on its reactive objects. (It’s a limitation of JavaScript).

It’s described in detail here: https://v2.vuejs.org/v2/guide/reactivity.html#Change-Detection-Caveats

The short version is: You have to do

created: function() {
  Vue.set(this.obj, 'obj2', {})
  Vue.set(this.obj.obj2, 'count', 0)
}

or

created: function() {
  Vue.set(this.obj, 'obj2', {
    count: 0
  })
}
Advertisement