Framework Comparison
A detailed feature matrix for all 10 frameworks on Cloudflare Workers. Use this to make an informed decision, not just go with the most popular option.
Feature Matrix
| Feature | React Router v7 | Astro | SvelteKit | TanStack Start | Hono | Next.js (OpenNext) | Nuxt | Qwik City | SolidStart | Vite+React SPA |
|---|---|---|---|---|---|---|---|---|---|---|
| SSR | Yes | Yes | Yes | Yes | Partial | Yes | Yes | Yes | Yes | No |
| SSG | Yes | Yes | Yes | Yes | No | Yes | Yes | Yes | Yes | N/A |
| Streaming | Yes | Yes | Yes | Yes | Yes | Yes | Yes | Yes | Yes | N/A |
| CF Vite Plugin | Yes | Yes | No | Yes | Optional | No | No | No | No | Yes |
| workerd in dev | Yes | Yes | No | Yes | Yes | No | No | No | No | Yes |
| File routing | Yes | Yes | Yes | Yes | No | Yes | Yes | Yes | Yes | No |
| Bindings in dev | Real | Real | Mocked | Real | Real | Mocked | Mocked | Mocked | Mocked | N/A |
| Worker entry point | Yes | No | No | Yes | Yes | Partial | No | No | No | Optional |
| Durable Objects colocate | Yes | No | No | Yes | Yes | No | No | No | No | No |
| Auto-detect deploy | Yes | Yes | Yes | Yes | No | No | Yes | Yes | Yes | Yes |
Edge-Friendliness Ranking
Ranked by how well each framework fits the Cloudflare Workers runtime model (V8 isolates, no Node.js, binding-first architecture).
Tier S: Born for Workers
-
Hono - Native Worker. No adapters, no polyfills, no impedance mismatch. If Workers had a default framework, this would be it. Limited to APIs and server-rendered HTML.
-
React Router v7 - CF Vite Plugin, Worker entry point access, real bindings in dev. The closest thing to a full-stack Hono with React UI.
-
TanStack Start - Same integration depth as React Router v7, plus type-safe routing. Newer, smaller community.
Tier A: Strong Integration
-
Astro - CF Vite Plugin (adapter v13), real
workerdin dev, zero-JS default. The best content framework on Cloudflare. -
Vite + React SPA - CF Vite Plugin for asset config. No server code to worry about. Zero edge-runtime issues because there’s no edge runtime.
Tier B: Works Well via Adapters
-
SvelteKit - Solid adapter, good Cloudflare support, but dev runs in Node.js. You’ll catch some bugs only after deploying.
-
Nuxt - Nitro server engine handles Workers well. Same dev/prod gap as SvelteKit.
-
SolidStart - Works on Cloudflare Pages. Smaller community, fewer examples.
-
Qwik City - Resumability model is interesting but the Cloudflare adapter is less mature. Targets Pages.
Tier C: Compatibility Layer
- Next.js (OpenNext) - Impressive feature coverage but fundamentally fighting the runtime. Node.js APIs shimmed, no
workerddev parity, community adapter with release lag.
Bundle Size Impact
Workers have a script size limit (3MB compressed free, 10MB paid). Framework server bundles vary significantly.
| Framework | Approx. Server Bundle | Risk at Free Tier |
|---|---|---|
| Hono | ~20KB | None |
| Vite+React SPA | 0 (no server) | None |
| Astro (static) | 0 (no server) | None |
| Astro (SSR) | ~100-300KB | Low |
| React Router v7 | ~200-500KB | Low |
| TanStack Start | ~200-500KB | Low |
| SvelteKit | ~200-400KB | Low |
| SolidStart | ~200-400KB | Low |
| Nuxt | ~500KB-1MB | Medium |
| Qwik City | ~300-600KB | Low-Medium |
| Next.js (OpenNext) | ~1-3MB | High (may need paid) |
Gotcha: These are approximate ranges. Your actual bundle depends on dependencies. Check with
wrangler deploy --dry-run.
Migration Paths from Next.js
Path 1: Keep Next.js (Least Effort)
Next.js app -> Add OpenNext -> Deploy to Workers
- Effort: Low
- Risk: Dev/prod parity gap, community adapter dependency
- Best when: Large existing codebase, can’t justify rewrite
Path 2: React Router v7 (Same Stack, Better Integration)
Next.js app -> Rewrite routes to React Router v7 -> CF Vite Plugin
- Effort: Medium-High
- Risk: Route migration, different data loading patterns
- Best when: Starting fresh or unhappy with Next.js lock-in
Path 3: Astro (Content Sites)
Next.js content site -> Rewrite pages to .astro -> Add React islands where needed
- Effort: Medium
- Risk: Different mental model (MPA vs SPA)
- Best when: Content-heavy site where most pages don’t need client JS
When NOT to Use Cloudflare
Be honest about the limits:
- Heavy compute: Image processing, video transcoding, ML inference exceeding Workers AI - use a traditional server
- Long-running processes: Workers have CPU time limits (10ms free, 30s paid per request)
- Large dependencies: If your
node_modulespull in native bindings (sharp,bcrypt,canvas), Workers won’t run them - Relational database needs beyond D1: D1 is SQLite-based. If you need Postgres features, you’ll need an external database and pay for latency
- WebSocket-heavy apps without Durable Objects: Standard Workers can’t hold persistent WebSocket connections. You need Durable Objects, which adds complexity