Next.js 13异步组件数据获取报错:无法渲染Promise对象
解决Next.js 13中客户端组件渲染异步组件的Promise错误
问题根源
Next.js 13 App Router里,带"use client"的客户端组件不能直接渲染异步组件——因为异步组件执行后会返回Promise,而React无法将Promise作为子元素渲染。你加的/* @ts-expect-error */注释只是跳过TypeScript检查,解决不了运行时的本质问题。
解决方案分两种场景:
场景1:Product组件不需要客户端交互(纯数据展示)
把Product改成服务端组件(去掉"use client"),然后在客户端的Page组件里用Suspense包裹它,处理加载状态:
Page组件(客户端):
"use client"; import { Suspense } from 'react'; import Product from './Product'; export default function Page() { return ( <Suspense fallback={<div>加载产品中...</div>}> <Product /> </Suspense> ); }
Product组件(服务端):
// 不要加"use client",默认就是服务端组件 export default async function Product() { // 这里写异步数据获取逻辑 const res = await fetch('你的接口地址', { cache: 'force-cache' }); const products = await res.json(); return ( <div className="product-list"> {products.map(product => ( <div key={product.id}>{product.name}</div> ))} </div> ); }
场景2:Product组件需要客户端交互(比如用useState/useEffect等hooks)
不能把组件写成async函数,要把异步数据逻辑放到useEffect里,或者用useSWR/react-query这类库管理数据:
Product组件(客户端):
"use client"; import { useState, useEffect } from 'react'; export default function Product() { const [products, setProducts] = useState([]); const [isLoading, setIsLoading] = useState(true); useEffect(() => { const fetchProducts = async () => { try { const res = await fetch('你的接口地址'); const data = await res.json(); setProducts(data); } catch (err) { console.error('获取数据失败:', err); } finally { setIsLoading(false); } }; fetchProducts(); }, []); if (isLoading) return <div>加载中...</div>; return ( <div className="product-list"> {products.map(product => ( <div key={product.id}>{product.name}</div> ))} </div> ); }
Page组件(客户端)直接引入:
"use client"; import Product from './Product'; export default function Page() { return <Product />; }
内容的提问来源于stack exchange,提问作者Arman Bagheri
相关产品推荐
相关产品推荐

