---
title: How to migrate from Railway to Vercel
description: Move an app from Railway to Vercel. Most Railpack-built apps deploy through framework detection with no container; Dockerfile apps move as Dockerfile.vercel. Map railway.json to vercel.json and cut over safely.
url: /kb/guide/migrate-railway-to-vercel
canonical_url: "https://vercel.com/kb/guide/migrate-railway-to-vercel"
published: 2026-08-11
last_updated: 2026-08-11
authors: Ben Sabic
related:
  - /kb/guide/does-vercel-support-docker-deployments
  - /docs/functions/container-images
  - /docs/container-registry
  - /docs/cron-jobs
  - /kb/guide/migrate-ghcr-to-vcr
  - /kb/guide/migrate-fly-io-to-vercel
  - /blog/dockerfile-on-vercel
install_vercel_plugin: npx plugins add vercel/vercel-plugin
---

To migrate from Railway to Vercel, pick your build path first: apps that Railway built with Railpack or Nixpacks usually deploy on Vercel through framework detection with no container at all, while apps built from a Dockerfile move by renaming it to `Dockerfile.vercel`. Either way, Vercel [builds on every commit and serves the app with automatic scaling](https://vercel.com/kb/guide/does-vercel-support-docker-deployments). Configuration moves from `railway.json` and dashboard variables to `vercel.json` and project environment variables, and stateful pieces such as Railway volumes and databases move to external backing services.

This guide maps each Railway concept to its Vercel equivalent, walks through the migration, and is direct about what doesn't carry over.

## Should your app move?

Vercel runs applications as stateless HTTP services, whether framework-built or containerized. Three questions decide the fit:

- **Does the app serve HTTP and keep no state between requests?** Sessions, uploads, and caches must live in a backing service, not on a Railway volume or in process memory.
  
- **Does it tolerate scale-to-zero?** If you already run Railway's app with sleeping enabled, the model is familiar: instances scale down when idle and back up when traffic increases. On Vercel this behavior is automatic rather than opt-in.
  
- **Is it request-driven?** Always-on background workers and queue consumers have no equivalent. Scheduled work does: Railway cron schedules map to Vercel cron jobs, covered in step 6.
  

## How Railway concepts map to Vercel

| Railway                                     | Vercel                                                                                                    |
| ------------------------------------------- | --------------------------------------------------------------------------------------------------------- |
| `railway.json` / `railway.toml`             | `vercel.json`                                                                                             |
| Railpack or Nixpacks builder                | Framework detection, zero configuration                                                                   |
| `builder: DOCKERFILE` with `dockerfilePath` | `Dockerfile.vercel`, or `entrypoint` per [service](https://vercel.com/docs/functions/container-images)    |
| `startCommand`                              | `CMD` / `ENTRYPOINT` in the image                                                                         |
| Injected `PORT` variable                    | `PORT` environment variable in project settings, default 80                                               |
| `railway up`                                | `git push`, or `vercel deploy` from the CLI                                                               |
| PR environments                             | Preview deployments, on by default for every commit                                                       |
| Service variables and reference variables   | Project environment variables, plus auto-generated cross-service variables                                |
| A project with several services             | One Vercel project with [services](https://vercel.com/docs/functions/container-images) routed by rewrites |
| App sleeping (opt-in)                       | Automatic scale-in after 5 minutes idle in production, 30 seconds in preview                              |
| Cron schedules                              | Vercel cron jobs in `vercel.json`                                                                         |
| Volumes                                     | External storage: databases, caches, or blob storage                                                      |
| `preDeployCommand`                          | CI step before deploy                                                                                     |

## Steps

### 1\. Pick your build path

Railway offers two ways to build, and each has a different destination on Vercel:

**If Railway built your app with Railpack or Nixpacks**, you likely don't need a container. Vercel's framework detection recognizes over 35 frameworks and configures builds automatically, which is the platform's preferred path. Import the repository and check whether detection picks the app up; a Next.js, Nuxt, SvelteKit, Astro, or similar app deploys with zero configuration, and `startCommand` becomes unnecessary because the framework preset handles startup.

**If Railway built from a Dockerfile**, or your app isn't a detected framework, copy the Dockerfile to `Dockerfile.vercel` at the project root. Vercel detects it, builds the image on every commit, pushes it to [Vercel Container Registry](https://vercel.com/docs/container-registry), and serves it on Fluid compute with Active CPU pricing. If your `railway.json` pointed at a non-standard path with `dockerfilePath`, that path moves to the service `entrypoint` in `vercel.json`. If Railway built your app from source but it isn't a framework Vercel detects, such as a plain Express or Flask server, this is the one case where migrating means writing a Dockerfile you didn't have: a few lines that install dependencies and start the server on `PORT`.

Either way, the port contract is the same one Railway taught you: the server reads the `PORT` environment variable. On Vercel it defaults to 80, and you can change it in project settings to match a hardcoded port; don't rely on an `ENV PORT` line in the image to change where traffic routes.

### 2\. Move the start command into the image

Railway lets `startCommand` in `railway.json` override how the container starts. Vercel runs the image as built, so anything in `startCommand` belongs in the Dockerfile's `CMD` or `ENTRYPOINT`. If your `startCommand` chained setup work before the server, such as `db:migrate && server`, split it: the server start goes in the image, and the migration moves to CI (step 5).

### 3\. Move configuration and variables

Recreate Railway's service variables as environment variables in your Vercel project settings, marking secrets as sensitive. Railway's reference variables, which share values between services in a project, map to Vercel's auto-generated cross-service environment variables: when you define multiple services, Vercel creates the variables each service needs to call the others, so URLs aren't hardcoded on either platform.

`railway.json` settings that configured the platform rather than the app have no destination: `restartPolicyType` and `healthcheckTimeout` are managed by the platform, and there's no `healthcheckPath` equivalent for containers, so validate deployments on their preview URLs instead.

### 4\. Move state out of the app

- **Railway Postgres, MySQL, or Redis** move to managed equivalents, such as services from the Vercel Marketplace, and the connection string becomes an environment variable. Export from Railway with standard tooling such as `pg_dump`, and import on the new host.
  
- **Volumes** have no equivalent. Files an app writes to a volume move to blob storage; anything else that must survive restarts moves to a database or cache.
  
- **In-process state** such as sessions moves to a managed cache.
  

### 5\. Replace preDeployCommand with a CI step

Railway runs `preDeployCommand` before each deployment goes live, most often for database migrations. Vercel has no deploy-time hook for containers, so run migrations from CI before the deploy, or as a separate pipeline step. This is also where any setup you removed from `startCommand` in step 2 belongs.

### 6\. Recreate cron schedules

Railway cron schedules run a service on a timer. On Vercel, [cron jobs](https://vercel.com/docs/cron-jobs) defined in `vercel.json` invoke an HTTP endpoint on a schedule, so a Railway cron service becomes a route in your app that performs the work when called. The scheduled task must fit the request model: it runs when invoked and finishes within function duration limits, rather than running as a standalone process.

### 7\. Verify and cut over

Railway's PR environments have a direct counterpart: every commit to a Vercel project gets a preview deployment with its own URL, no configuration required. Test the app on preview URLs against production backing services in read-only paths first, then shift traffic by updating DNS. Keep the Railway services running until Vercel serves production traffic cleanly, then remove them. For container apps, `vercel dev` runs the image locally with your Docker daemon, so behavior differences reproduce on your machine rather than in production.

## What doesn't map from Railway

- **Volumes.** No attached persistent disk exists. Data on volumes must move to external storage before migrating.
  
- **Always-on workers.** Background processes that aren't request-driven don't fit. Restructure them around HTTP invocation, keep them on Railway, or use cron jobs where a schedule fits.
  
- `**preDeployCommand**`**.** No deploy hook; migrations belong in CI.
  
- `**healthcheckPath**`**.** There's no container health-check configuration; preview deployments are where you validate before traffic shifts.
  
- **Two networking features.** Secure Compute and Static IPs aren't supported with custom container images yet. If external services allowlist your Railway egress today, plan around that.
  

## Frequently asked questions

### Do I need a Dockerfile to move from Railway to Vercel?

Only if you had one on Railway, or your app isn't a framework Vercel detects. Apps that Railway built with Railpack or Nixpacks usually deploy through Vercel's framework detection with zero configuration. Everything else moves with a `Dockerfile.vercel`.

### What replaces railway.json on Vercel?

`vercel.json` covers routing, services, and cron jobs, while build settings come from framework detection or the Dockerfile, and runtime settings such as `PORT` live in project environment variables. Settings like `restartPolicyType` and `healthcheckTimeout` have no equivalent because the platform manages instances.

### What happens to my Railway Postgres?

It moves to a managed database, such as one from the Vercel Marketplace. Export with standard tooling like `pg_dump`, import on the new host, and update the connection string environment variable. Databases don't run on Vercel itself.

### Do I keep PR environments?

Yes, and without setup. Vercel creates a preview deployment with its own URL for every commit by default, which covers what Railway's PR environments provide.

### How does pricing compare to Railway's usage-based model?

Both platforms bill on usage rather than fixed instances, so the model is familiar. On Vercel, containerized apps run as Vercel Functions with Active CPU pricing: cost follows the CPU time your code uses, and idle instances scale to zero automatically rather than as an opt-in.

## Related resources

- [Does Vercel support Docker deployments?](https://vercel.com/kb/guide/does-vercel-support-docker-deployments) and [How to migrate from GHCR to Vercel Container Registry](https://vercel.com/kb/guide/migrate-ghcr-to-vcr) guides
  
- [How do I migrate from Fly.io to Vercel?](https://vercel.com/kb/guide/migrate-fly-io-to-vercel) guide
  
- [Run any Dockerfile on Vercel](https://vercel.com/blog/dockerfile-on-vercel) on the Vercel blog
  
- [Container images](https://vercel.com/docs/functions/container-images), [Vercel Container Registry](https://vercel.com/docs/container-registry), and [Cron jobs](https://vercel.com/docs/cron-jobs) in the Vercel Docs
  
- [7 ways to use Docker containers on Vercel](https://vercel.com/i/7-ways-to-use-docker-containers-on-vercel)