Partial Prerendering (PPR) in Next.js

From the Next.js cheat sheet · Advanced Routing & Modern Features · verified Jul 2026

Partial Prerendering (PPR)

Static shell + streamed dynamic holes in the same response

tsx
// next.config.ts  (Next.js 16 - PPR via Cache Components)
import type { NextConfig } from 'next'
const nextConfig: NextConfig = {
  cacheComponents: true, // replaces experimental.ppr / dynamicIO / useCache
}
export default nextConfig

// app/product/[id]/page.tsx  (no per-route flag needed in 16)
import { Suspense } from 'react'

export default async function Page({ params }: { params: Promise<{ id: string }> }) {
  const { id } = await params
  return (
    <main>
      <ProductDetails id={id} />          {/* prerendered shell */}
      <Suspense fallback={<CartFallback />}>
        <Cart />                          {/* dynamic hole, streamed in */}
      </Suspense>
    </main>
  )
}
💡 Static shell from the CDN + dynamic holes streamed in one response
📌 Requires <Suspense> around every dynamic chunk - else falls back to full dynamic
⚡ Enabled by cacheComponents: true in 16 (experimental_ppr was removed)
🎯 Killer for product pages, dashboards, anywhere you mix shared + personal UI
pprperformanceexperimental

More Next.js tasks

Back to the full Next.js cheat sheet