5👍
First please be careful as Suspense
is still experimental feature and can change any time…
In order to async setup
to work, the component itself must be inside <suspense>
….your component is not inside <suspense>
– it contains <suspense>
component (which of course can not work until the component is created and that can happen only after your async setup
resolves). You must place <suspense>
as a child of <router-view>
– see the docs
Here is a working demo (if you see import declarations may only appear at top level of a module
first, just reload the right pane using the reload icon – seems like some glitch in the Matrix)
// App.vue
<router-view v-slot="{ Component }">
<suspense timeout="0">
<template #default>
<component :is="Component"></component>
</template>
<template #fallback>
<div>Loading...</div>
</template>
</suspense>
</router-view>
// Home.vue
<template>
<div class="home">
<pre>{{ result }}</pre>
</div>
</template>
<script>
import { defineComponent, ref } from "vue";
export default defineComponent({
async setup() {
const result = ref();
const response = await fetch("https://api.publicapis.org/entries");
result.value = await response.json();
return { result };
},
});
</script>
Notice timeout="0"
on suspense
– it seems there is a timeout
for switching to a "loading" state (probably to avoid too much screen flickering when async components resolve quickly enough)
A
timeout
prop can be specified – if a pending tree remains pending past the timeout threshold, the active tree will be unmounted and be replaced by the fallback tree.
I’m unable to find what is the default value for timeout
right now. Feel free to tune it for your own needs…