Ad

Vue.js Async Component Not Updating Template

- 1 answer

I have a Vue Component where I do a bunch of async calls, which should then populate my template. However, nothing seems to be getting updated, even though I can see in the console that my data is coming back. I'm pretty new to Vue, so I must be missing something. Here's a simplified version of my code:

<template>
  <div id="my_component">
        <div v-bind:class="{ hidden: !isLoading }">
      <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" style="margin:auto;background:#fff;display:block;" width="200px" height="200px" viewBox="0 0 100 100" preserveAspectRatio="xMidYMid">
        <circle cx="50" cy="50" fill="none" stroke="#1ba4de" stroke-width="4" r="15" stroke-dasharray="70.68583470577033 25.561944901923447">
          <animateTransform attributeName="transform" type="rotate" repeatCount="indefinite" dur="0.9803921568627451s" values="0 50 50;360 50 50" keyTimes="0;1"></animateTransform>
        </circle>
      </svg>
    </div>

    <div v-bind:class="{ hidden: isLoading }">
      <h1>{{ result.title }}</h1>
    </div>
  </div>
</template>


<script>
export default {
  name: 'MyComponent',
  data () {
    return {
      isLoading: true,
      result: null
    }
  },
  async created () {
    this.result = await myLongRunningAsyncFunction();
    this.isLoading = true;
    console.log(this.result) // Logs result of myLongRunningAsyncFunction()
  }
  methods: {
    myLongRunningAsyncFunction: async function() {
     // Make a bunch of API calls and get some data
    }
  }
}
</script>
Ad

Answer

Instead of toggle a class you can use v-if to hide/show elements. I am not sure what your hide class looks like but i guess its something like display: none witch is less efficient.

<div v-if="!isLoading">
    <h1>{{ result.title }}</h1>
</div>

You also need to set isLoading to false

async created () {
    this.result = await myLongRunningAsyncFunction();
    this.isLoading = false;
    console.log(this.result) // Logs result of myLongRunningAsyncFunction()
}

Also in your first div, this would look much nicer:

 <div v-bind:class="{ hidden: !isLoading }">

to this:

 <div v-if="isLoading">
Ad
source: stackoverflow.com
Ad