Deploy to Cloudflare with adapter-cloudflare
SvelteKit’s Cloudflare adapter outputs a Worker that runs your SSR routes on workerd and serves prerendered/static assets alongside it.
Install and configure
npm i -D @sveltejs/adapter-cloudflare
Kit 3 keeps config in the Vite plugin options (see Kit 3 Changes):
// vite.config.js
import adapter from '@sveltejs/adapter-cloudflare';
import { sveltekit } from '@sveltejs/kit/vite';
import { defineConfig } from 'vite';
export default defineConfig({
plugins: [
sveltekit({
adapter: adapter({
config: undefined, // path to wrangler config, if non-default
platformProxy: { // bindings in dev via wrangler proxy
configPath: undefined,
environment: undefined,
persist: undefined,
},
fallback: 'plaintext', // SPA fallback mode for non-prerendered routes
routes: {
include: ['/*'],
exclude: ['<all>'], // static assets win over SSR
},
}),
}),
],
});
What the adapter gives you
- Bindings: access KV, R2, D1, Durable Objects through
event.platform.envin load functions and endpoints platformProxy: duringvite dev, bindings are proxied from your wrangler config so dev behaves like prod (Miniflare-backed)- Routes split:
include/excludedecide which requests hit the Worker vs static assets;<all>exclusion keeps asset serving fast - Deploy:
wrangler deployaftervite build
Gotcha: runtime is
workerd, not Node. Node-only dependencies fail at deploy even if dev works. Check the Cloudflare frameworks topic for the runtime constraints.
When to prefer this over adapter-node
- Your target is Cloudflare’s network (edge SSR, no servers to run)
- Your app uses Cloudflare storage primitives directly
- You want the cheapest always-on hosting for spiky traffic
For a self-hosted Docker lane (the lab default for apps), use adapter-node instead. For a comparison of every framework on Cloudflare, see the frameworks landscape.