With Static Rendering, routes are rendered at build time, or in the background after data revalidation. The result is cached and can be pushed to a Content Delivery Network (CDN). This optimization allows you to share the result of the rendering work between users and server requests. Static rendering is useful when a route has data that is not personalized to the user and can be known at build time, such as a static blog post or a product page.
With Dynamic Rendering, routes are rendered for each user at request time. Dynamic rendering is useful when a route has data that is personalized to the user or has information that can only be known at request time, such as cookies or the URL's search params.
In Next.js, you can have dynamically rendered routes that have both cached and uncached data. This is because the RSC Payload and data are cached separately. This allows you to opt into dynamic rendering without worrying about the performance impact of fetching all the data at request time.
During rendering, if a dynamic function or uncached data request is discovered, Next.js will switch to dynamically rendering the whole route.
With Streaming, routes are rendered on the server at request time. The work is split into chunks and streamed to the client as it becomes ready. This allows the user to see a preview of the page before it's fully rendered. Streaming is useful for lower-priority UI, or UI that depends on slower data fetches that would block rendering for the whole route.