为何Next.js 13中Material UI Typography需在客户端组件渲染?
在Next.js 13服务端组件中使用Material UI组件无需添加"use client"的解决方案
问题原因
Material UI(MUI)的大部分组件(包括Typography)依赖React客户端特性(如状态hooks、DOM API)或Emotion样式系统的客户端运行时,直接在Next.js 13的服务端组件中使用会因缺少客户端环境导致崩溃,添加"use client"声明后组件转为客户端组件,就能正常运行。
可行解决方案
1. 配置MUI服务端渲染支持(推荐)
MUI v5.14.0及以上版本开始支持Next.js 13的App Router和服务端组件,需正确配置Emotion的服务端渲染:
步骤1:安装依赖
npm install @emotion/server @emotion/react
步骤2:在根layout中配置Emotion CacheProvider
在app/layout.tsx中设置服务端渲染的Emotion缓存:
import { CacheProvider } from '@emotion/react'; import createCache from '@emotion/cache'; // 创建Emotion缓存实例 const cache = createCache({ key: 'mui-server-side' }); export default function RootLayout({ children }: { children: React.ReactNode }) { return ( <html lang="en"> <body> <CacheProvider value={cache}>{children}</CacheProvider> </body> </html> ); }
步骤3:使用MUI组件
现在可以在服务端组件中直接导入并使用Typography,无需添加"use client":
import { Typography } from "@mui/material"; import * as React from "react"; const AppFooter: React.FC = () => { return ( <footer> <Typography component="p" className="text-center bg-primary text-secondary"> This is the website footer. </Typography> </footer> ); } export default AppFooter;
2. 封装MUI组件为客户端组件(折中方案)
如果暂时无法升级MUI版本或配置服务端渲染,可以将MUI组件封装在客户端组件中,服务端组件引用封装后的组件:
创建ClientTypography.tsx(客户端组件)
"use client"; import { Typography } from "@mui/material"; export default Typography;
在服务端组件中引用
import Typography from './ClientTypography'; import * as React from "react"; const AppFooter: React.FC = () => { return ( <footer> <Typography component="p" className="text-center bg-primary text-secondary"> This is the website footer. </Typography> </footer> ); } export default AppFooter;
3. 使用MUI Base无样式组件
如果不需要MUI的默认样式,可以使用MUI Base的无样式基础组件,这类组件不依赖客户端hooks,可直接在服务端组件中使用:
npm install @mui/base
import { Typography } from "@mui/base/Typography"; import * as React from "react"; const AppFooter: React.FC = () => { return ( <footer> <Typography component="p" className="text-center bg-primary text-secondary"> This is the website footer. </Typography> </footer> ); } export default AppFooter;
注意事项
- 确保MUI版本≥v5.14.0才能完整支持Next.js 13服务端组件
- 部分复杂MUI组件(如
Dialog、Snackbar)仍依赖客户端交互,可能还是需要"use client"声明
内容的提问来源于stack exchange,提问作者Emad Younan
相关产品推荐
相关产品推荐

