Upgrading PostgreSQL Major Versions
Railway can upgrade a PostgreSQL service to a newer major version in place, using pg_upgrade. The database is stopped for the duration of the upgrade — typically a few minutes, depending on data size — and comes back on the new major with all its data intact.
This works for standalone Postgres services and for Postgres HA clusters. On a cluster, the primary is upgraded first and every replica is rebuilt from it on the new major; the cluster stays paused (no automatic failover) until every member is back on the same major.
Prerequisites
- Official Railway image only —
ghcr.io/railwayapp-templates/postgres-sslor a Postgres HA cluster onghcr.io/railwayapp-templates/postgres-ha/postgres-patroni. Custom images are not supported. - Pinned version tag — the service must be on a specific major (
:latestis not supported). - Supported source majors: 14 through 17, upgrading to any newer major Railway publishes.
Step 1 — Review the Preflight Report
Open your Postgres service, navigate to Database → Config → Major Version Upgrade. Railway runs a read-only preflight check against the live database and reports each result:
| Check | What it looks for |
|---|---|
reg* column types | Columns storing regproc, regoper, and similar catalog-OID types an upgrade cannot preserve (only checked below major 16) |
aclitem column types | Columns using the aclitem type, whose internal format changed in PostgreSQL 16 (only checked below major 16) |
| Prepared transactions | Open two-phase-commit transactions, which must be committed or rolled back first |
| Logical replication slots | Slots are not carried over — consumers must re-create them after the upgrade |
| Password authentication | Roles still using md5 password auth, which should move to SCRAM first |
| Event triggers | Present triggers should be reviewed for compatibility with a catalog restore |
| Extensions | Each installed extension is checked against what the image ships: missing entirely (blocker) or behind the image's version (run ALTER EXTENSION … UPDATE) |
| Data size | Informational — pg_upgrade needs free volume space for the new catalog |
A blocker prevents starting the upgrade until it's resolved. A warning doesn't block the upgrade but is worth reviewing first. Click Re-run after making a fix to refresh the report.
Step 2 — Start the Upgrade
Choose the target major version and click Upgrade to PostgreSQL <version>. The confirmation dialog summarizes what happens:
- The database is stopped while
pg_upgraderuns, so it will be briefly unavailable. - A backup is taken before the upgrade and another once the new major is serving — a restore point on either side.
- The upgrade only starts if preflight reports no blockers.
Once confirmed, Railway takes the pre-upgrade backup, runs the upgrade job against the volume, and redeploys the service on the new major's image. A progress panel on the same page tracks each phase.
On a Postgres HA cluster, this additionally pauses cluster failover, upgrades the primary, then rebuilds each replica from it on the new major before resuming failover — the whole cluster moves together.
Step 3 — Revert, if Needed
For a limited window after the upgrade completes, a banner offers Revert and discard changes — this restores the pre-upgrade backup and returns the service (or every member of an HA cluster) to the previous major. Any writes made after the upgrade are lost, since the backup point predates them.
If the upgrade itself fails, the same revert action is offered from the failure banner, and the pre-upgrade backup is restored automatically to recover the service.
Manual Image Edits
Changing the service's image tag directly (outside this flow) to jump a Postgres major does not run pg_upgrade and does not migrate the data directory — the database will very likely refuse to start, or start against data it can't safely read. Railway warns about this in the image settings when the new tag's major doesn't match the running data, and steers you back to this flow. Use it unless the volume is empty or you already know the data is compatible with the new major.
Troubleshooting
A replica in an HA cluster won't come back after an upgrade or revert. Railway retries automatically; if a replica was offline for an unrelated reason during the operation, it may need a redeploy once it's back to pick up the rebuild. Contact support if a replica stays unhealthy after that.
Extensions report "missing from the image." The target major's image doesn't ship that extension. Check the extension's own release notes for major-version support before upgrading, or remove it first if it's unused.
Logical replication slots after an upgrade. These are not preserved across a major upgrade — re-create any logical slots your consumers depend on once the new major is serving.