opsdocsConsole

Ops platform / Concepts

Deployments and previews

From a push to a running service, rolling back, promoting, and an environment per pull request.

Updated 13 Oct 2026View as Markdown

A deployment

A push to a branch an environment follows starts a build for every service that builds from the repository. Deployments lists them, and each one shows its steps:

stepwhat happens
clonethe commit is fetched through the GitHub App
checksops waits for the commit's GitHub checks to pass
buildthe image is built from the service's Dockerfile
scanthe image is scanned for known vulnerabilities
pushthe image is stored in ops's registry
signops signs the image; only signed images are deployed
deploythe service is updated to the new image
healthops watches the rollout until it is healthy
docsin production, when the project file names a docs folder, it is published; see Publish docs

The docs step runs after the service is healthy, and a broken docs folder fails only that step: the deployment stands and you get a notification.

Builds run one at a time. The commit on GitHub shows a deployment status and a check run, so the pull request says what is live.

Which checks count. By default a build waits for the checks the branch protection requires, or, where GitHub cannot say, for every check on the commit. List them yourself with checks in the project file; checks: [] waits for none. A check that fails refuses the build, and one that never reports times out after two hours.

Healthy means every replica is running and stays running for the service's health window, 120 seconds unless you set deploy.health_window_secs. Give the image a HEALTHCHECK so a container that starts but cannot serve counts as unhealthy.

Rollback

A rollout that does not come up healthy is rolled back to the newest healthy image automatically, and you get a notification. To go back by hand:

sh
ops rollback web                          # the newest healthy image before this one
ops rollback web --digest sha256:4f1c...  # a specific image

A deployment's page has Roll back now while its rollout is unhealthy.

Deploying by hand

ops deploy puts a build that already exists on a service, without a push:

sh
ops deploy web --commit 7c1d0e2            # the newest build of that commit
ops deploy web --build 412                 # a build by its id
ops deploy web --digest sha256:4f1c...     # an image by its digest

Promote

Promote moves the exact images of one environment into another, with no rebuild. It is how a release goes from staging to production when production should run what staging was tested with:

sh
ops promote --from staging --to production --dry-run   # what would change
ops promote --from staging --to production

The console has the same under Settings, Promote.

Previews

When a project has a staging or development environment, every pull request gets a preview environment of its own, preview-<n>, with its own hostname. It is built from the pull request's branch and updated on each push to it. Ops posts one comment on the pull request with the address, the database, the build and the expiry, and keeps that comment current.

  • A preview copies its services and domain from the environment that follows the pull request's base branch, with one replica each.
  • Its variables are copied from staging, else development, and never from production.
  • A database that keeps a template gets a fresh copy of that template in the preview; a database without one is not in the preview. A SQLite database starts empty. Keep only seed data in a template, see Databases.
  • A pull request from a fork never gets a preview.
  • A preview is removed when the pull request closes, or three days after its last push.

The number of previews and how long they last are set in Settings, Previews. When the limit is reached, the pull request says so instead of getting one.