Vue Js 2 provide cannot be updated in Parent

36 Views Asked by At

I'm trying to use the provide functions in Vue.js 2.7 and i want to update one of the props through an async function but it doesn't update the injection in the children

Parent.vue

<template>
    <Child />
</template>

<script>
export default {
    provide(){
        return {
            typesTabs: null,
            instanceTypeToAdd: null,
            buttonInstanceTypeToAdd: null,
            updateProvidedPropValue: this.updateProvidedPropValue
        }
    },
    mounted(){
       this.fetchInstances()
    },
    methods: {
        updateProvidedPropValue(propName, value) {
            this[propName] = value
        },
        async fetchInstances() {
            axios.get().then(() => {
                this.typesTabs =
                    JSON.parse(JSON.stringify(res.data.expense_income_type_consts))
            })
        }
    }
}
</script>

Child.vue

<template> 
    <div 
        v-for="tab in typesTabs" 
        @click="updateProvidedPropValue('instanceTypeToAdd', tab)"
    > 
        {{ tab.name }} 
    </div>
</template>

<script>
    export default {
        inject: ['typesTabs', 'instanceTypeToAdd', 'updateProvidedPropValue']
    }
</script>

while the updateProvidedPropValue works properly IF i give the typesTabs object hard coded, when it's loading asynchronously the typesTabs doesn't contain anything so i can't change the instanceTypeToAdd.

I tried to console.log(this.typesTabs) in Parent.vue right after the axios request and it's filling the prop (typesTabs) propperly, but does not update to show content in children.

1

There are 1 best solutions below

0
yoduh On BEST ANSWER

From the documentation.

Note: the provide and inject bindings are NOT reactive. This is intentional. However, if you pass down an observed object, properties on that object do remain reactive.

You can use a data and computed property together as a work-around

import { computed } from 'vue';

...

provide() {
  return {
    typesTabs: computed(() => this.tabs),
    instanceTypeToAdd: null,
    buttonInstanceTypeToAdd: null,
    updateProvidedPropValue: this.updateProvidedPropValue
  };
},
data() {
  return {
    tabs: []
  };
},
axios.get().then(() => {
  this.tabs =
    JSON.parse(JSON.stringify(res.data.expense_income_type_consts))
})