Last updated on 18th May 2026

Deployment Checks

Deployment Checks let you gate a deployment with validations that run on the deployment worker, either before the build pipeline starts or after every server has received its files. They are designed for the two questions you ask most often around a deploy:

  • Before the build runs: is it safe to deploy right now? (No uncommitted changes on the target server, no maintenance flag set, no in-flight migration, etc.)
  • After the deploy finishes: did it actually work? (Site returns 200, healthcheck endpoint reports healthy, smoke command succeeds.)

Deployment Checks are currently in beta. Enable beta features on your account to see the "Deployment Checks" entry in the project sidebar.

How a check fits into a deployment

Every check has a stage and a type.

Stages:

  • Pre-build – runs at the very start of a deployment, before the build pipeline begins. A failing pre-build check aborts the deployment cleanly, before any build resources are spent. This is the right place to detect things like uncommitted changes the customer made directly on the server, or a maintenance flag that says "don't deploy right now".
  • Post-deploy – runs after every server has received its files, before the deployment is marked complete. A failing post-deploy check marks the deployment as failed and fires the usual failure notifications (email, Slack, webhook). The files stay on the server – Deployment Checks do not roll the deploy back, they alert you so you can react.

Types:

  • SSH – runs an arbitrary command on one or more SSH-capable servers in the project. A non-zero exit aborts (pre-build) or fails (post-deploy) the deployment. Output is captured into the deploy log in a console-style block.
  • HTTP – sends a GET or HEAD request to a URL and checks the response status (and, optionally, that the body contains a specific substring). Use this for maintenance-flag endpoints, public healthchecks, or any URL-based signal.

The SSH type only applies to projects with at least one SSH-capable server. HTTP checks work for any project type – including FTP, ElasticBeanstalk, Heroku, and the cloud-storage protocols – because they run from the deployment worker, not on a target server.

Worked examples

Detecting drift before deploying

A common case for Drupal, WordPress and similar CMS sites: an operator edits a file directly on the server (a quick config tweak, a hotfix on a plugin) and forgets to push it back into git. The next deploy would overwrite their change.

A pre-build SSH check that runs against the existing release directory will catch this:

git diff --quiet && git diff --cached --quiet || exit 1

If the working tree on the server is clean, both git diff calls exit 0 and the deploy proceeds. If anything is uncommitted, the check exits non-zero and the deploy is aborted before the build kicks off – no wasted build minutes, no overwritten changes.

Maintenance-mode flag

If you publish a /maintenance.json endpoint that returns 200 when maintenance is on, a pre-build HTTP check can refuse to deploy on top of it:

  • Method: GET
  • URL: https://example.com/maintenance.json
  • Expected status: 404

If the maintenance flag is up, the endpoint returns 200, the expected 404 doesn't match, and the deploy aborts. When maintenance is taken down, the endpoint 404s, the check passes, and deploys resume.

Post-deploy smoke test

A post-deploy HTTP check that hits your homepage with an expected 200 is a cheap canary against a broken deploy. Pair it with a body match (e.g. "healthy" from a /healthcheck endpoint) if your app exposes a richer signal.

Server scoping for SSH checks

SSH checks can run on every SSH-capable server in the project, on a specific subset, or on the servers in a server group. The scoping uses the same picker as pre/post-deployment commands, so it should already feel familiar.

A few things to know:

  • If you create an SSH check on a project that has no SSH-capable servers (for example, an FTP-only or Heroku-only project), the check will be marked as skipped on every deploy – it shows up in the deploy log as a neutral, grey note rather than as a green pass or a red failure.
  • The pre/post-deployment commands you have today still work exactly as before. Deployment Checks sit outside the file transfer phase – pre-build runs before the build server is touched, and post-deploy runs after the last server's transfer completes.

Template variables

Both SSH commands and HTTP URLs support the same template variables as pre/post-deployment commands. The variables most useful for checks are:

  • %current_path% – the active release directory on the target server
  • %release_path% – the directory of the release being deployed
  • %branch% – the branch being deployed
  • %startrev% / %endrev% – the SHAs that bound the deploy

For example, cd %current_path% && ./scripts/config-check.sh runs a config-validation script that lives in your repository.

Timeouts and output

Every check has a per-check timeout (default 30 seconds, hard cap 10 minutes). A check that doesn't finish in time is treated as a failed check.

Output is bounded:

  • SSH check output is capped at 1MB per execution. Anything beyond that is truncated and the deploy log notes the truncation.
  • HTTP check responses capture up to 64KB of the response body.

What fires when a check fails

Pre-build failure:

  • The deployment is aborted before the build server is contacted.
  • The deployment is marked as failed.
  • Existing failure notifications fire (any integration with "send on failure" enabled).

Post-deploy failure:

  • All transfers have already completed by this point. Files stay on the server.
  • The deployment is marked as failed.
  • Existing failure notifications fire.

If you only want to be notified about check failures (and not all deployment failures), the simplest pattern today is a dedicated integration scoped to failure notifications. Per-check-type notification events are on the roadmap.

API

Deployment Checks are managed through the standard project API alongside build commands and pre/post-deployment commands. Each project exposes /projects/:project_id/deployment_checks for full CRUD. See the API reference for the request and response shapes.