'Unexpected effect: Making a copy of an object modifies it

Context:

I have a component whichj emits data to the parent. Parent has two default objects-An empty array, and another object which contains default values, which are used to add a new element to the array using the data passed.

Template:

<billing-search
    :search-term="searchText"
    :show-modal="showBillingModal"
    @closeModal="CloseBillingModal"
    @selectedAnItem="AddSelectedItem"
/>

Initial data:

data() {
    return {
        billitems: [],
        billitem_def: {
            invitem: null,
            procitem: null,
            stockid: null,
            qty: 0,
            unitprice: 0,
            discpercent: 0,
            disc: 0,
        }
    }
},
    

My method in the parent triggered on emiting from the component, is this:

AddSelectedItem(data) {
    console.log(`In AddSelectedItem`);
    console.log(`this.billitems was `, this.billitems);
    console.log(`Got data passed by component:`, data);
    let newitem = this.billitem_def
    console.log(`this.billitems was `, this.billitems);
    newitem.invitem = data.item
    newitem.stockid = data.storeitem
    newitem.unitprice =  newitem.stockid.mrp
    console.log(`Added new item to billing list:`);
    console.log(newitem);
    this.billitems.push(newitem)
    console.log(`this.billitems is now `, this.billitems);
    console.log(`this.billitem_def is `, this.billitem_def);
},

See an example of console log:

In AddSelectedItem
BillingBlock.vue?670b:173 this.billitems was  
0:
    disc: 0
    discpercent: 0
    invitem: {id: 50, name: 'Waxonil Activ Ear Drops', description: 'Adult ear drops', itemtype: 4, clinic: 10, …}
    procitem: null
    qty: 0
    stockid: {id: 432, entry: {…}, item: {…}, quantity: 30, stock: 21, …}
    unitprice: "119.30"
BillingBlock.vue?670b:174 Got data passed by component: 
{
    item: {
        clinic: 10
        description: "Adult ear drops"
        drugid: null
        id: 50
        isOpen: true
        itemtype: 4
        name: "Waxonil Activ Ear Drops"
        storeitem: (13) [{…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}]
    },
    storeitem: {
        batchnum: "SW135"
        entry: {id: 275, entry_number: 'WjazQPLxb', reference_number: '', invoice_number: 'A-50864', entry_date: '2021-12-20', …}
        expirydate: "2024-08-21"
        id: 432
        item: {id: 50, name: 'Waxonil Activ Ear Drops', description: 'Adult ear drops', itemtype: 4, clinic: 10, …}
        manufacturedate: null
    }
}
BillingBlock.vue?670b:177 this.billitems was  
Proxy {
    0:
    disc: 0
    discpercent: 0
    invitem: {id: 50, name: 'Waxonil Activ Ear Drops', description: 'Adult ear drops', itemtype: 4, clinic: 10, …}
    procitem: null
    qty: 0
    stockid: {id: 432, entry: {…}, item: {…}, quantity: 30, stock: 21, …}
    unitprice: "119.30"
}
BillingBlock.vue?670b:181 Added new item to billing list:
BillingBlock.vue?670b:182 
Proxy {invitem: {…}, procitem: null, stockid: {…}, qty: 0, unitprice: '119.30', …}
BillingBlock.vue?670b:185 this.billitems is now  
Proxy {0: {…}}
BillingBlock.vue?670b:186 this.billitem_def is  
Proxy { invitem: {… }, procitem: null, stockid: {… }, qty: 0, unitprice: '119.30', … }

Problems with this:

  1. The this.billitems was shows data even before it is being assigned, instead of an empty array
  2. this.billitem_def was set to some null values initially in the data part. It was not meant to get values, but to serve as a template of default data. Though I had let newitem = this.billitem_def, how is this.billitem_def's data getting modified? I dont have code anywhere in the project assigning this.billitem_def to anything else.


Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source