After 20+ client projects on Next.js, I switched most of my work to Vite + React. The honest reason: most clients don't need SSR, and Next.js makes you pay for SSR even when you're not using it — in build time, in deployment complexity, in mental overhead, and in money. Vite gives me sub-second dev server starts, smaller bundles, deploy-anywhere flexibility, and a stack a junior can hand off in a week. I still reach for Next.js when SEO, edge rendering, or co-located backend code is genuinely the requirement. The rule I now use is: pick the simplest tool that solves the actual problem in front of you, not the most powerful tool in case the problem grows.
I've been a Next.js advocate for years. Server-side rendering, file-based routing, API routes, image optimization, the App Router — it's a powerful framework, and Vercel has done a remarkable job of pushing the web forward through it. For long-form content sites, marketing pages, and large multi-tenant SaaS, it's an excellent default.
But after shipping more than twenty client projects across portfolios, dashboards, admin panels, internal tools, and small SaaS products, I noticed an uncomfortable pattern: almost none of my clients actually needed SSR. They needed a fast app, a clean handoff, cheap hosting, and a stack their next developer could understand without a course.
What they were getting was an SSR-shaped framework that added complexity I had to keep explaining away. The first time I shipped a Vite + React + Supabase project end to end and watched the dev server boot in 200ms and the production build deploy to a static host for free, I stopped pretending. For SPAs, Next.js is overkill, and the overkill has a cost.
Next.js is built around the assumption that some pages will be server-rendered. Even if you push everything to the client, you're still inside that assumption. You pay for it in:
None of this is fatal. A lot of it is acceptable for the right project. But for an SPA that's going to live behind auth and ship to a handful of users, every one of those costs is being paid for a benefit that's never collected.
Build speed. Vite's dev server starts in under 300 milliseconds on my machine. Cold start. Next.js takes between 3 and 8 seconds on the same hardware. When you're iterating fast — making a small change, checking the browser, making another small change — that gap compounds into real wall-clock hours over a week of work.
Simplicity. There is no \`getServerSideProps\