|Docs

Roll Back a Bad Deploy Fast

deploymentsrollbackincident-responsehealthchecks

A rollback on Railway restores a previous deployment's Docker image and its custom variables as a new active deployment. There is no rebuild, so it completes in seconds. When a deploy breaks production, rolling back is almost always faster than pushing a fix.

Rollback is one of three recovery actions Railway gives you, alongside redeploy and restart. This guide covers when each one applies, plus how to configure healthcheck-gated deploys so a broken release never receives traffic.

Roll back from the dashboard

  1. Open your project and click the affected service.
  2. Go to the Deployments tab.
  3. Find the last known-good deployment in the list.
  4. Click the three dots at the end of that deployment and select Rollback.
  5. Confirm the rollback.

Railway restores both the Docker image and the custom variables from that deployment, so if the outage was caused by a bad environment variable change rather than bad code, the rollback reverts that too.

That stored image is what makes rollback fast: there's no build step, and the rollback is live as soon as the container starts.

Which deployments can you roll back to?

Rollback depends on Railway still having the old image. Railway retains images for a period after a deployment is removed, based on your plan:

PlanImage retention
Free / Trial24 hours
Hobby72 hours
Pro120 hours
Enterprise360 hours

Deployments older than your plan's retention window cannot be restored, and the Rollback option will not appear on them. For those, use Redeploy instead: it rebuilds the image from the deployment's original source code with its original variables. The result is the same version of your app, but you wait for a build.

See the image retention policy for details.

Rollback vs redeploy vs restart

Railway has three recovery actions. Picking the right one saves time.

ActionWhat it doesBuild?Use when
RollbackRestores a previous deployment's image and variablesNoThe latest deploy broke something and an older version worked
RedeployCreates a new deployment from the same source and configurationYesThe image expired from retention, or you want a fresh build of the same commit
RestartRestarts the current deployment's existing containerNoThe app wedged at runtime (memory leak, stuck connection) but the code is fine

Redeploy and restart are available from the same three-dots menu on the Deployments tab, and restart also appears inline on a Crashed deployment. Before reaching that state, Railway automatically restarts crashed deployments up to 10 times, depending on your restart policy, then marks them Crashed and notifies project members by email and webhook.

One more distinction: Redeploy on a deployment reuses that deployment's exact code and configuration. To deploy the latest commit from your default branch instead, open the Command Palette (CMD + K) and choose "Deploy Latest Commit".

Roll back or redeploy from the CLI

The dashboard is the only place to roll back to an arbitrary older deployment. The CLI covers the redeploy and restart cases:

# Redeploy the most recent deployment (triggers a rebuild)
railway redeploy --service backend --yes

# Restart the current deployment without rebuilding
railway restart --service backend --yes

railway restart reuses the existing image and waits for the deployment to become healthy before the command completes. railway redeploy creates a new deployment from the same source, which includes a build.

To inspect deployment history and grab IDs for log correlation:

# List recent deployments with IDs, statuses, and timestamps
railway deployment list

# View logs for a specific deployment
railway logs <deployment-id>

railway deployment list --json is useful in scripts, for example to fetch the latest deployment ID with jq.

Prevent bad deploys with a healthcheck

A rollback fixes the incident after users saw it. A healthcheck-gated deploy prevents the incident.

When a service has a healthcheck path configured, Railway queries that endpoint on every new deployment and only switches traffic once it returns HTTP 200. If the endpoint does not return 200 within the timeout, the deploy is marked failed and the previous deployment keeps serving traffic.

To set it up:

  1. Add an endpoint to your app (for example /health) that returns status 200 when the app is ready. Your app must listen on the PORT variable Railway injects, since the healthcheck targets that port.
  2. In the service settings, set the healthcheck path to /health.
  3. Optionally adjust the timeout. The default is 300 seconds; change it in settings or with the RAILWAY_HEALTHCHECK_TIMEOUT_SEC variable.

Two caveats:

  • The healthcheck runs only at deploy time. Railway does not monitor the endpoint continuously after the deployment goes live.
  • Services with an attached volume cannot run two deployments at once, so a volume-backed service has a brief window of downtime on every deploy even with a healthcheck configured.

Healthcheck requests come from the hostname healthcheck.railway.app. If your framework restricts allowed hosts, add it to the allowlist or the check will fail with errors like "failed with service unavailable".

See healthchecks for full configuration details.

What to do when a deploy goes bad

This order minimizes downtime:

  1. Confirm the deploy is the cause. Check whether errors started right after the latest deployment went live. Deployment timestamps are on the Deployments tab.
  2. Roll back first, debug second. Click the three dots on the last good deployment and confirm the rollback. Users stop seeing errors in seconds.
  3. Diagnose from the failed deployment's logs. The failed deployment and its build and runtime logs remain available after the rollback.
  4. Fix forward. Push the corrected commit. The new deploy replaces the rolled-back one through your normal flow.
  5. Add a healthcheck if you did not have one. If the bad deploy would have failed a /health probe, a healthcheck would have blocked it automatically.

Next steps