← Back

Static vs Dynamic Rendering

What triggers dynamic rendering, when Suspense shows fallbacks, updateTag() for ISR.

PublishedMarch 5, 2026149 words
Edit

Static vs Dynamic Rendering

With cacheComponents: true, Next.js defaults to dynamic. You opt into static with "use cache".

Static: The Blog Homepage

async function BlogList() { const posts = await getPublishedPosts(); // Uses "use cache" return posts.map(post => <PostCard post={post} />); }
async function BlogList() { const posts = await getPublishedPosts(); // Uses "use cache" return posts.map(post => <PostCard post={post}

Because getPublishedPosts uses "use cache", results are cached. No loading states needed—content is ready.

Dynamic: The Dashboard

export default function DashboardPage({ searchParams }) { return ( <Suspense fallback={<PostListSkeleton />}> <PostList

The searchParams prop triggers dynamic rendering. Each request fetches fresh data, so Suspense fallbacks show while loading.

What Makes a Page Dynamic?

  • Reading searchParams or params
  • Calling cookies() or headers()
  • Data fetches without "use cache"

Invalidating Static Content

export async function createPost(formData: FormData) { await prisma.post.create({ data }); updateTag('posts'); }

After updateTag, the next request regenerates the content.

/>
)
;
}
searchParams
=
{
searchParams
}
/>
</
Suspense
>
)
;
}
export default function DashboardPage({ searchParams }) { return ( <Suspense fallback={<PostListSkeleton />}> <PostList searchParams={searchParams} /> </Suspense> ); }
export
async
function
createPost
(
formData
:
FormData
)
{
await
prisma
.
post
.
create
(
{
data
}
)
;
updateTag
(
'posts'
)
;
}