Suspense 怎么用?

让组件"等待"的时候有个交代

先说结论:Suspense 允许组件在等待异步操作时,暂停渲染并展示一个后备内容。

经典用法:路由懒加载

配合 React.lazy 实现代码分割:

import React, { Suspense } from 'react';

// 这个组件的代码只有在渲染时才会下载
const LazyComponent = React.lazy(() => import('./OtherComponent'));

function MyComponent() {
  return (
    <Suspense fallback={<div>加载中...</div>}>
      <LazyComponent />
    </Suspense>
  );
}

进阶用法:数据请求

React 18 和 Next.js 支持 Suspense 等待数据。

以前:Fetch-on-Render

  1. 组件渲染
  2. useEffect 发请求
  3. Loading
  4. 显示数据

现在:Render-as-you-fetch

  1. 开始渲染
  2. 发现数据没准备好
  3. 抛出一个 Promise
  4. React 捕获 Promise,暂停渲染,显示 Fallback
  5. Promise 完成后,React 重新渲染,显示数据

Streaming SSR

服务端渲染中,Suspense 允许分块流式传输

  • 不用等整个页面的接口都回来
  • 先发 Header、Sidebar
  • 中间内容等接口好了再推过去
  • 首屏更快

注意点

Suspense 捕获的是组件抛出的 Promise。

普通的 axios.get 放在 useEffect 里不会触发 Suspense,必须配合支持 Suspense 的库(如 React Query、SWR、Next.js)使用。

总结

用法场景
lazy + Suspense路由懒加载
数据请求等待接口
Streaming SSR服务端分块推送

Suspense 就是让等待变得优雅——有东西看,不白屏。