Problem to modify a variable with Vue.js

1

I have a problem with Vue js: I try to do something like a list of notes. I have a json array where all the notes will be saved and a json where the note that the person wants to create is saved. But the problem is:
After doing a push to the json array, it is added perfectly, but after modifying the value in the json the json array is automatically modified.
I can not modify the json without modifying the value in the array.
PD: the method that the push does is activated when I click on a button
I will leave here the most relevant code, if you need more information I will gladly provide it.

el: '#app',
    data: {
        hasError: 0,
        typeError: '',
        noteSelected: null,
        note: {
            title: '',
            content: '',
            tags: [],
            tagsString: ''
        },
        notes: [{
            title: 'titulo de una nota',
            content: 'contenido de una nota',
            tags: ['nota', 'contenido'],
            tagsString: ''
        }]
    },
   methods:{
      newNote: function() {
            if (this.validate() === true && this.noteSelected === null) {
                this.addTags();
                this.noteSelected = this.note;
                this.notes.push(noteSelected);
            }
        },
}
    
asked by user23245 21.11.2016 в 02:49
source

1 answer

1

The issue is not with Vue.js, it's with Javascript.

In Javascript (and other languages) something curious happens: arguments of complex type are passed by reference and primitives by value . The fix clave -> valor in Javascript (being objects / JSON) are complex types, therefore, their values are passed as reference. (Reference to the index in memory).

What does this have to do with your problem?

Everything.

Then why is this happening?

Where to copy the value of this.note to this.noteSelected with an equality ( this.noteSelected = this.note ) and then making a array.push() to object this.notes the value is not passed from one object to another if not a reference to the memory index where said value is. When trying to modify the value in any of these, the value in the memory space is modified and therefore it looks as if it was modified in both arrays.

Blablabla and the solution is?

You can use a small " hack " to get the value and not the object reference by converting it to String with JSON.stringify() and then back to a% object json with JSON.parse() ( JSON.parse(JSON.stringify(JSON)) )

In your case it would look like this:

newNote: function() {
  if (this.validate() === true && this.noteSelected === null) {
    this.addTags();
    this.noteSelected = JSON.parse(JSON.stringify(this.note)); // <- Aquí el cambio: 
    this.notes.push(noteSelected);
  }
},

Another solution, if you have an instance of jQuery would be to use the jQuery.extend() function which would be almost the same, only that the line in question would look like this: this.noteSelected = jQuery.extend({}, this.note);

Here I leave a link to the jsbin reproducing the "phenomenon" that occurs link

It is not complex to understand, it has its logic although it is somewhat confusing. I hope it solves your problem, and even more, that it clarifies your confusion.

    
answered by 21.11.2016 в 15:12