什么是 Suspense 组件,它是如何实现的?

1.7k words

Vue3中的 Suspense 组件是用于处理异步依赖的一种机制。当你有异步组件或者在setup函数中有异步操作并希望在这些异步依赖加载完成前显示一个“fallback”内容(如加载指示器),你可以使用 Suspense

工作原理:

  • 捕捉异步组件: Suspense 可以捕捉其作用域内的异步组件。当这些组件还未解析完成(通常是网络加载)时,Suspense 会渲染它的 fallback 插槽内容。
  • async setup() 配合:在组件的 setup 函数中,你也可以返回一个Promise。如果你这样做了,Suspense 也会等待这个 Promise 解析完成才渲染实际内容。
  • 多层嵌套: suspense 组件可以嵌套使用,这样内层的 Suspense 可以被外层的Suspense“捕获”。
  • Reactivity:由于 suapense 是与 Vue 的响应式系统集成的,所以一旦异步依赖完成,suspenae 会自动重新渲染,替换fa11back为实际内容。
  • 插槽: suspense 使用了两个插槽 default 和 fallback。defau1插槽用于你希望渲染的实际内容,【a1Iback 插槽用于在等待异步依赖期间展示的内容。

示例:

在这个例子中, AsyncComponent 是一个异步组件。只有当这个组件完全加载和初始化后, Suspense 才会从展示”Loading.”切换到展示这个组件。总的来说, Suspense 组件提供了一种优雅和集成的方式来处理异步依赖,使得用户界面在等待这些依赖时仍然响应和友好。

异步组件:AsyncComponent

在顶层 <script setup> 组件中直接使用 await,那么该组件为异步组件

1
2
3
4
5
6
7
8
9
10
11
<script setup>
const msg = await new Promise((resolve) => {
setTimeout(() => {
resolve('Hi, I"m a async component')
}, 3000)
})
</script>

<template>
{{ msg }}
</template>

或者返回一个异步的 async setup() 方法

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<script setup>
export default {
async setup() {
const msg = await new Promise((resolve) => {
setTimeout(() => {
resolve('Hi, I"m a async component')
}, 3000)
})

return {
msg,
}
},
}
</script>

<template>
{{ msg }}
</template>

使用示例: Suspense

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<script setup>
import { defineAsyncComponent } from 'vue'

const AsyncComponent = defineAsyncComponent(() => import('./components/MyComponent.vue'))
</script>

<template>
<Suspense>
<template *default>
<AsyncComponent />
</template>
<template #fallback>
<div>Loading...</div>
</template>
</Suspense>
</template>
Comments