The right way to host a SvelteKit app depends on how your routes run. A static site needs only files. An SSR app needs a server or platform function for each request. Choose that model first, then install the adapter that matches your hosting provider.
SvelteKit can deploy to static hosting, Vercel, Netlify, Cloudflare, or a standard Node server. The build command may look similar, but the output and runtime are different. Use this workflow to select the adapter, configure the project, deploy it, and fix common production errors.
Choose the deployment model first
Your application usually fits one of two models. The choice affects routing, environment variables, API calls, and hosting costs.
Static sites use prebuilt files
A static SvelteKit site generates HTML, CSS, JavaScript, and other assets during the build. The host serves those files through a CDN or web server.
This model fits:
- Marketing sites
- Documentation
- Blogs
- Portfolio sites
- Product landing pages
- Content that changes only during a deployment
Static output doesn’t run server code for each visitor. You can’t depend on server-only form actions, private environment variables, or request-time database queries unless you move those operations into a separate API.
Use @sveltejs/adapter-static for this model. The official static site documentation explains how SvelteKit creates a collection of deployable files.
SSR apps need a runtime
Server-side rendering generates a response when a user requests a route. The server can read cookies, call a database, process form actions, and use private environment variables.
SSR fits:
- Authenticated dashboards
- Applications with user-specific pages
- Sites with request-time data
- Server actions
- API endpoints inside the SvelteKit project
- Pages that must reflect current database values
The host must provide a JavaScript runtime. That runtime may be a Node server, a serverless function, or an edge worker. Use a provider adapter that produces the format your host expects.
Don’t select static output because it is cheaper or easier if your application needs server behavior. A static build can hide that mistake until a route fails in production.
Select the SvelteKit adapter
Adapters convert the SvelteKit build into deployment output for a target platform. SvelteKit’s adapter reference lists the official options and their intended environments.
| Hosting target | Adapter | Output |
|---|---|---|
| Static file host | @sveltejs/adapter-static | Prebuilt files |
| Standard Node server | @sveltejs/adapter-node | Standalone Node server |
| Vercel | @sveltejs/adapter-vercel | Vercel functions or platform output |
| Netlify | @sveltejs/adapter-netlify | Netlify functions and assets |
| Cloudflare Pages or Workers | @sveltejs/adapter-cloudflare | Cloudflare-compatible output |
New projects often start with adapter-auto. It detects supported deployment environments. That works during early development, but a pinned provider adapter gives your lockfile and CI process a fixed target.
Install the adapter for your host
Install one adapter as a development dependency. Don’t install several and switch between them without changing the configuration.
For a static site:
npm install -D @sveltejs/adapter-static
For a Node server:
npm install -D @sveltejs/adapter-node
For a Vercel deployment:
npm install -D @sveltejs/adapter-vercel
Then update svelte.config.js. The adapter belongs inside the kit configuration.
Use adapter-auto only when you need it
adapter-auto is useful when you are testing several supported hosts. It reduces initial configuration, but it doesn’t expose every platform option. For example, provider-specific settings may require the actual Vercel or Netlify adapter.
The adapter-auto documentation recommends installing the platform adapter after you choose a deployment target. Do that before your production deployment.
Host a SvelteKit app as a static site
Use static output when every required page can be generated during the build.
Install the adapter, then configure it like this:
import adapter from '@sveltejs/adapter-static';
const config = {
kit: {
adapter: adapter()
}
};
export default config;
Set prerendering at the route level when appropriate. To prerender the complete application, place this in src/routes/+layout.js:
export const prerender = true;
You can also prerender selected pages instead of the entire site. This is useful when some routes require server rendering.
Run the production build locally:
npm run build
The adapter creates the output directory defined by its configuration. Upload that directory to your static host, or connect the repository to a provider that runs the build automatically.
Static hosting works well on Cloudflare Pages, Netlify, Vercel, GitHub Pages, object storage with a CDN, and other file hosts. The provider settings differ, but the application output is the same type of asset bundle.
Check dynamic routes before deployment
A dynamic route such as /blog/[slug] needs known entries during prerendering. SvelteKit must discover those paths while building the site.
If the route list comes from an API or database, confirm that the build environment can access it. If it can’t, use SSR or generate the content before the SvelteKit build.
A static deployment also needs a fallback strategy for client-side navigation. Configure a fallback only when your host requires one. A fallback can make unknown URLs appear to work while hiding missing prerendered pages, so test direct requests as well as internal links.
Deploy SSR with Vercel, Netlify, or Cloudflare
Managed platforms remove most server maintenance. They build your repository and deploy server routes to their own runtime.
Vercel
Install @sveltejs/adapter-vercel and use it in svelte.config.js:
import adapter from '@sveltejs/adapter-vercel';
const config = {
kit: {
adapter: adapter()
}
};
export default config;
Connect the Git repository in Vercel, set the required environment variables, and deploy. The Vercel SvelteKit guide documents the platform setup and supported deployment behavior.
Vercel can deploy static routes as assets and server routes as functions. Review route-specific deployment settings if you need a particular runtime or function configuration. Test cookies, form actions, streaming, and database connections in a preview deployment before changing production traffic.
Netlify
Use @sveltejs/adapter-netlify for Netlify:
import adapter from '@sveltejs/adapter-netlify';
const config = {
kit: {
adapter: adapter()
}
};
export default config;
The official Netlify adapter documentation covers the expected output and available configuration. Netlify handles the build and publishes the generated assets. Server-rendered routes run through Netlify’s serverless infrastructure.
Check the function runtime, region, timeout, and environment variables in the Netlify project settings. A database connection that works locally may need a pooled connection or an HTTP-based database client in a serverless environment.
Cloudflare Pages and Workers
Cloudflare uses @sveltejs/adapter-cloudflare for SvelteKit deployments. The Cloudflare SvelteKit deployment guide covers the current Pages setup.
Cloudflare’s runtime isn’t a standard Node server. Packages that depend on Node-specific APIs may fail unless the selected runtime supports them. Test file access, database clients, cryptography, and native modules before deployment.
Use Cloudflare bindings for services such as databases, object storage, and key-value storage when your application needs them. Keep provider-specific code inside a small server module so it doesn’t spread through every route.
Run SvelteKit on a Node server
Choose @sveltejs/adapter-node when you control the server, container, virtual machine, or managed Node host.
Install it:
npm install -D @sveltejs/adapter-node
Configure the adapter:
import adapter from '@sveltejs/adapter-node';
const config = {
kit: {
adapter: adapter()
}
};
export default config;
Build and start the application:
npm run build
node build
The generated server listens using the host and port values supplied by the environment. Your hosting service usually provides those values. Don’t hard-code a local development port in production.
Add a process manager
A Node server needs a process manager or container platform that restarts it after a crash and starts it after a machine reboot. Common options include Docker, systemd, and PM2.
Place a reverse proxy such as Nginx or Caddy in front of the Node process when you manage a virtual machine. The proxy handles TLS and forwards requests to the internal application port.
Set the public origin when the application needs to create absolute URLs:
ORIGIN=https://example.com node build
Use your host’s secret configuration for ORIGIN, database credentials, and API keys. Never commit production values to .env files.
Configure environment variables correctly
SvelteKit separates environment variables by visibility and timing. The import you choose determines where a value can be used.
Use $env/static/private for private values known during the build. Use $env/dynamic/private for private values read at runtime by server code. Public values use the corresponding $env/static/public and $env/dynamic/public modules.
The SvelteKit environment variable documentation explains these modules and their build-time behavior.
Keep secrets on the server
Database passwords, private API tokens, and signing keys belong in private modules. Import them only from server files such as +page.server.js, +server.js, or other server-only modules.
Don’t place a private import in a component or shared module that can be included in browser code. A build error may catch some mistakes, but the safest approach is to keep server code and browser code clearly separated.
Understand prerendering limits
A prerendered page is generated during the build. It can’t depend on a runtime-only value in the same way as an SSR page.
If a value changes between deployments, use an SSR route or the environment module that matches the documented prerendering behavior. SvelteKit 2 also changed how dynamic environment variables work during prerendering, so test a production build instead of relying only on npm run dev.
Deployment checklist
Run this checklist before you point a domain at the new deployment.
- Confirm whether the application is static, SSR, or a mixture of both.
- Install and pin the adapter for the selected host.
- Run
npm run checkand fix type or route errors. - Run
npm run buildin a clean environment. - Test the production build locally when your adapter supports it.
- Add all required environment variables to the hosting provider.
- Confirm that public variables use the expected
PUBLIC_naming convention where required. - Test direct requests to dynamic routes, not only navigation from the home page.
- Test form actions, cookies, authentication, API endpoints, and database calls.
- Check the browser console and server logs after deployment.
- Confirm the custom domain, HTTPS certificate, redirects, and canonical URLs.
- Keep the last trusted deployment available for rollback.
Treat deployment records like operational records. Save the adapter version, build command, environment variable names, provider settings, and deployment URL. If a release fails, you need to reproduce the last working setup.
Fix common SvelteKit deployment errors
The host returns a 404 for dynamic routes
This usually means the route wasn’t prerendered or the host lacks the required fallback configuration. Decide whether the route should be static or server-rendered. Then check the adapter and the host’s routing rules.
Server-only code appears in the browser
Move private imports into a server route or server load function. Check shared modules imported by components. A server-only dependency can enter browser code indirectly through one shared import.
The build works locally but fails on the host
Compare Node versions, package lockfiles, environment variables, and build commands. Run the build with production-like variables locally. Missing build-time values are a common cause of prerender failures.
Database requests fail after deployment
Check the provider runtime first. A Node database client may not work in an edge worker. Serverless functions may also create too many short-lived connections. Use the database provider’s supported connection method for the selected runtime.
Environment variables are undefined
Confirm the variable name, scope, deployment environment, and import path. A value in your local .env file doesn’t automatically exist in Vercel, Netlify, Cloudflare, or a Node server. Rebuild when using static environment imports.
Assets load from the wrong path
Review the base path, trailing slash behavior, and asset configuration. This often appears after deploying under a subdirectory instead of the domain root. Test the generated HTML and network requests in a production build.
Conclusion
To host a SvelteKit app reliably, choose the runtime before choosing the provider. Use adapter-static for prebuilt files, a platform adapter for managed SSR, and adapter-node when you control the server.
Pin the adapter, test production output, configure environment variables in the host, and verify direct route requests. Most deployment failures come from a mismatch between the app’s runtime needs and the adapter’s output. Get that decision right first, and the remaining deployment work becomes a controlled configuration task.
